Commit 3a91295e authored by Joachim's avatar Joachim
Browse files

Merge branch 'master' of https://github.com/davisking/dlib

parents 22164e5d 75f66582
......@@ -18,8 +18,9 @@
#include <algorithm>
#include <cmath>
#include <memory>
#include "../matrix.h"
#include "../smart_pointers.h"
#include "optimization_bobyqa_abstract.h"
#include "optimization.h"
......@@ -59,7 +60,7 @@ namespace dlib
{
const unsigned long n = x.size();
const unsigned long w_size = (npt+5)*(npt+n)+3*n*(n+5)/2;
scoped_ptr<doublereal[]> w(new doublereal[w_size]);
std::unique_ptr<doublereal[]> w(new doublereal[w_size]);
// make these temporary matrices becuse U might be some
// kind of matrix_exp that doesn't support taking the address
......
......@@ -151,6 +151,7 @@
#include <deque>
#include <complex>
#include <map>
#include <memory>
#include <set>
#include <limits>
#include "uintn.h"
......@@ -160,7 +161,6 @@
#include "unicode.h"
#include "byte_orderer.h"
#include "float_details.h"
#include "smart_pointers/shared_ptr.h"
namespace dlib
{
......@@ -1490,7 +1490,7 @@ namespace dlib
}
private:
shared_ptr<std::ofstream> fout;
std::shared_ptr<std::ofstream> fout;
};
class proxy_deserialize
......@@ -1513,7 +1513,7 @@ namespace dlib
}
private:
shared_ptr<std::ifstream> fin;
std::shared_ptr<std::ifstream> fin;
};
inline proxy_serialize serialize(const std::string& filename)
......
......@@ -5,13 +5,14 @@
#include "server_kernel_abstract.h"
#include <memory>
#include <string>
#include "../threads.h"
#include "../sockets.h"
#include <string>
#include "../algs.h"
#include "../set.h"
#include "../logger.h"
#include "../smart_pointers.h"
namespace dlib
......@@ -209,8 +210,8 @@ namespace dlib
int max_connections;
mutex max_connections_mutex;
signaler thread_count_zero;
scoped_ptr<thread_function> async_start_thread;
scoped_ptr<listener> sock;
std::unique_ptr<thread_function> async_start_thread;
std::unique_ptr<listener> sock;
unsigned long graceful_close_timeout;
......
......@@ -135,6 +135,65 @@ namespace dlib
typedef simd4i simd4f_bool;
#elif defined(DLIB_HAVE_NEON)
class simd4f
{
public:
typedef float type;
inline simd4f() {}
inline simd4f(float f) { x = vdupq_n_f32(f); }
inline simd4f(float r0, float r1, float r2, float r3)
{
float __attribute__ ((aligned (16))) data[4] = { r0, r1, r2, r3 };
x = vld1q_f32(data);
}
inline simd4f(const float32x4_t& val):x(val) {}
inline simd4f(const simd4i& val):x(vcvtq_f32_s32(val)) {}
inline simd4f& operator=(const simd4i& val)
{
x = simd4f(val);
return *this;
}
inline simd4f& operator=(const float& val)
{
x = simd4f(val);
return *this;
}
inline simd4f& operator=(const float32x4_t& val)
{
x = val;
return *this;
}
inline operator float32x4_t() const { return x; }
// truncate to 32bit integers
inline operator int32x4_t() const { return vcvtq_s32_f32(x); }
inline void load_aligned(const type* ptr) { x = vld1q_f32(ptr); }
inline void store_aligned(type* ptr) const { vst1q_f32(ptr, x); }
inline void load(const type* ptr) { x = vld1q_f32(ptr); }
inline void store(type* ptr) const { vst1q_f32(ptr, x); }
inline unsigned int size() const { return 4; }
inline float operator[](unsigned int idx) const
{
float temp[4];
store(temp);
return temp[idx];
}
private:
float32x4_t x;
};
typedef simd4i simd4f_bool;
#else
class simd4f
{
......@@ -212,6 +271,7 @@ namespace dlib
float x[4];
};
class simd4f_bool
{
public:
......@@ -224,6 +284,7 @@ namespace dlib
private:
bool x[4];
};
#endif
// ----------------------------------------------------------------------------------------
......@@ -244,6 +305,8 @@ namespace dlib
return _mm_add_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_add(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vaddq_f32(lhs, rhs);
#else
return simd4f(lhs[0]+rhs[0],
lhs[1]+rhs[1],
......@@ -262,6 +325,8 @@ namespace dlib
return _mm_sub_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_sub(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vsubq_f32(lhs, rhs);
#else
return simd4f(lhs[0]-rhs[0],
lhs[1]-rhs[1],
......@@ -280,6 +345,8 @@ namespace dlib
return _mm_mul_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_mul(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vmulq_f32(lhs, rhs);
#else
return simd4f(lhs[0]*rhs[0],
lhs[1]*rhs[1],
......@@ -298,6 +365,12 @@ namespace dlib
return _mm_div_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_div(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
float32x4_t reciprocal = vrecpeq_f32(rhs);
reciprocal = vmulq_f32(vrecpsq_f32(rhs, reciprocal), reciprocal);
reciprocal = vmulq_f32(vrecpsq_f32(rhs, reciprocal), reciprocal);
float32x4_t result = vmulq_f32(lhs,reciprocal);
return result;
#else
return simd4f(lhs[0]/rhs[0],
lhs[1]/rhs[1],
......@@ -305,17 +378,19 @@ namespace dlib
lhs[3]/rhs[3]);
#endif
}
inline simd4f& operator/= (simd4f& lhs, const simd4f& rhs)
inline simd4f& operator/= (simd4f& lhs, const simd4f& rhs)
{ lhs = lhs / rhs; return lhs; }
// ----------------------------------------------------------------------------------------
inline simd4f_bool operator== (const simd4f& lhs, const simd4f& rhs)
{
inline simd4f_bool operator== (const simd4f& lhs, const simd4f& rhs)
{
#ifdef DLIB_HAVE_SSE2
return _mm_cmpeq_ps(lhs, rhs);
return _mm_cmpeq_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_cmpeq(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return (int32x4_t)vceqq_f32(lhs, rhs);
#else
return simd4f_bool(lhs[0]==rhs[0],
lhs[1]==rhs[1],
......@@ -326,11 +401,11 @@ namespace dlib
// ----------------------------------------------------------------------------------------
inline simd4f_bool operator!= (const simd4f& lhs, const simd4f& rhs)
{
inline simd4f_bool operator!= (const simd4f& lhs, const simd4f& rhs)
{
#ifdef DLIB_HAVE_SSE2
return _mm_cmpneq_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return _mm_cmpneq_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX) || defined(DLIB_HAVE_NEON)
return ~(lhs==rhs); // simd4f_bool is simd4i typedef, can use ~
#else
return simd4f_bool(lhs[0]!=rhs[0],
......@@ -342,12 +417,14 @@ namespace dlib
// ----------------------------------------------------------------------------------------
inline simd4f_bool operator< (const simd4f& lhs, const simd4f& rhs)
{
inline simd4f_bool operator< (const simd4f& lhs, const simd4f& rhs)
{
#ifdef DLIB_HAVE_SSE2
return _mm_cmplt_ps(lhs, rhs);
return _mm_cmplt_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_cmplt(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return (int32x4_t)vcltq_f32(lhs, rhs);
#else
return simd4f_bool(lhs[0]<rhs[0],
lhs[1]<rhs[1],
......@@ -365,12 +442,14 @@ namespace dlib
// ----------------------------------------------------------------------------------------
inline simd4f_bool operator<= (const simd4f& lhs, const simd4f& rhs)
{
inline simd4f_bool operator<= (const simd4f& lhs, const simd4f& rhs)
{
#ifdef DLIB_HAVE_SSE2
return _mm_cmple_ps(lhs, rhs);
return _mm_cmple_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_cmple(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return (int32x4_t)vcleq_f32(lhs, rhs);
#else
return simd4f_bool(lhs[0]<=rhs[0],
lhs[1]<=rhs[1],
......@@ -381,19 +460,21 @@ namespace dlib
// ----------------------------------------------------------------------------------------
inline simd4f_bool operator>= (const simd4f& lhs, const simd4f& rhs)
{
inline simd4f_bool operator>= (const simd4f& lhs, const simd4f& rhs)
{
return rhs <= lhs;
}
// ----------------------------------------------------------------------------------------
inline simd4f min (const simd4f& lhs, const simd4f& rhs)
{
inline simd4f min (const simd4f& lhs, const simd4f& rhs)
{
#ifdef DLIB_HAVE_SSE2
return _mm_min_ps(lhs, rhs);
return _mm_min_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_min(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vminq_f32(lhs, rhs);
#else
return simd4f(std::min(lhs[0],rhs[0]),
std::min(lhs[1],rhs[1]),
......@@ -404,12 +485,14 @@ namespace dlib
// ----------------------------------------------------------------------------------------
inline simd4f max (const simd4f& lhs, const simd4f& rhs)
{
inline simd4f max (const simd4f& lhs, const simd4f& rhs)
{
#ifdef DLIB_HAVE_SSE2
return _mm_max_ps(lhs, rhs);
return _mm_max_ps(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_max(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vmaxq_f32(lhs, rhs);
#else
return simd4f(std::max(lhs[0],rhs[0]),
std::max(lhs[1],rhs[1]),
......@@ -420,12 +503,17 @@ namespace dlib
// ----------------------------------------------------------------------------------------
inline simd4f reciprocal (const simd4f& item)
{
inline simd4f reciprocal (const simd4f& item)
{
#ifdef DLIB_HAVE_SSE2
return _mm_rcp_ps(item);
return _mm_rcp_ps(item);
#elif defined(DLIB_HAVE_VSX)
return vec_re(item());
#elif defined(DLIB_HAVE_NEON)
float32x4_t estimate = vrecpeq_f32(item);
estimate = vmulq_f32(vrecpsq_f32(estimate , item), estimate );
estimate = vmulq_f32(vrecpsq_f32(estimate , item), estimate );
return estimate ;
#else
return simd4f(1.0f/item[0],
1.0f/item[1],
......@@ -436,12 +524,17 @@ namespace dlib
// ----------------------------------------------------------------------------------------
inline simd4f reciprocal_sqrt (const simd4f& item)
{
inline simd4f reciprocal_sqrt (const simd4f& item)
{
#ifdef DLIB_HAVE_SSE2
return _mm_rsqrt_ps(item);
return _mm_rsqrt_ps(item);
#elif defined(DLIB_HAVE_VSX)
return vec_rsqrt(item());
#elif defined(DLIB_HAVE_NEON)
float32x4_t estimate = vrsqrteq_f32(item);
simd4f estimate2 = vmulq_f32(estimate, item);
estimate = vmulq_f32(estimate, vrsqrtsq_f32(estimate2, estimate));
return estimate;
#else
return simd4f(1.0f/std::sqrt(item[0]),
1.0f/std::sqrt(item[1]),
......@@ -464,6 +557,9 @@ namespace dlib
simd4f temp = _mm_add_ps(item,_mm_movehl_ps(item,item));
simd4f temp2 = _mm_shuffle_ps(temp,temp,1);
return _mm_cvtss_f32(_mm_add_ss(temp,temp2));
#elif defined(DLIB_HAVE_NEON)
float32x2_t r = vadd_f32(vget_high_f32(item), vget_low_f32(item));
return vget_lane_f32(vpadd_f32(r, r), 0);
#else
return item[0]+item[1]+item[2]+item[3];
#endif
......@@ -479,7 +575,7 @@ namespace dlib
return sum(lhs*rhs);
#endif
}
// ----------------------------------------------------------------------------------------
inline simd4f sqrt(const simd4f& item)
......@@ -488,6 +584,20 @@ namespace dlib
return _mm_sqrt_ps(item);
#elif defined(DLIB_HAVE_VSX)
return vec_sqrt(item());
#elif defined(DLIB_HAVE_NEON)
float32x4_t q_step_0 = vrsqrteq_f32(item);
float32x4_t q_step_parm0 = vmulq_f32(item, q_step_0);
float32x4_t q_step_result0 = vrsqrtsq_f32(q_step_parm0, q_step_0);
float32x4_t q_step_1 = vmulq_f32(q_step_0, q_step_result0);
float32x4_t q_step_parm1 = vmulq_f32(item, q_step_1);
float32x4_t q_step_result1 = vrsqrtsq_f32(q_step_parm1, q_step_1);
float32x4_t q_step_2 = vmulq_f32(q_step_1, q_step_result1);
float32x4_t res3 = vmulq_f32(item, q_step_2);
// normalize sqrt(0)=0
uint32x4_t zcomp = vceqq_f32(vdupq_n_f32(0), item);
float32x4_t rcorr = vbslq_f32(zcomp, item, res3);
return rcorr;
#else
return simd4f(std::sqrt(item[0]),
std::sqrt(item[1]),
......@@ -502,7 +612,7 @@ namespace dlib
{
#ifdef DLIB_HAVE_SSE41
return _mm_ceil_ps(item);
#elif defined(DLIB_HAVE_SSE2)
#elif defined(DLIB_HAVE_SSE2) || defined(DLIB_HAVE_NEON)
float temp[4];
item.store(temp);
temp[0] = std::ceil(temp[0]);
......@@ -528,7 +638,7 @@ namespace dlib
{
#ifdef DLIB_HAVE_SSE41
return _mm_floor_ps(item);
#elif defined(DLIB_HAVE_SSE2)
#elif defined(DLIB_HAVE_SSE2) || defined(DLIB_HAVE_NEON)
float temp[4];
item.store(temp);
temp[0] = std::floor(temp[0]);
......@@ -557,6 +667,8 @@ namespace dlib
return _mm_blendv_ps(b,a,cmp);
#elif defined(DLIB_HAVE_SSE2)
return _mm_or_ps(_mm_and_ps(cmp,a) , _mm_andnot_ps(cmp,b));
#elif defined(DLIB_HAVE_NEON)
return vbslq_f32(cmp, a, b);
#else
return simd4f(cmp[0]?a[0]:b[0],
cmp[1]?a[1]:b[1],
......
......@@ -54,9 +54,9 @@ namespace dlib
vector bool int b;
signed int x[4];
} v4i;
v4i x;
public:
inline simd4i() : x{0,0,0,0} { }
inline simd4i(const simd4i& v) : x(v.x) { }
......@@ -81,13 +81,55 @@ namespace dlib
inline void load(const int32* ptr) { x.v = vec_vsx_ld(0, ptr); }
inline void store(int32* ptr) const { vec_vsx_st(x.v, 0, ptr); }
struct rawarray
{
v4i v;
};
inline simd4i(const rawarray& a) : x{a.v} { }
};
#elif defined(DLIB_HAVE_NEON)
class simd4i
{
public:
typedef int32 type;
inline simd4i() {}
inline simd4i(int32 f) { x = vdupq_n_s32(f); }
inline simd4i(int32 r0, int32 r1, int32 r2, int32 r3)
{
int32 __attribute__((aligned(16))) data[4] = { r0, r1, r2, r3 };
x = vld1q_s32(data);
}
inline simd4i(const int32x4_t& val):x(val) {}
inline simd4i& operator=(const int32x4_t& val)
{
x = val;
return *this;
}
inline operator int32x4_t() const { return x; }
inline operator uint32x4_t() const { return (uint32x4_t)x; }
inline void load_aligned(const type* ptr) { x = vld1q_s32(ptr); }
inline void store_aligned(type* ptr) const { vst1q_s32(ptr, x); }
inline void load(const type* ptr) { x = vld1q_s32(ptr); }
inline void store(type* ptr) const { vst1q_s32(ptr, x); }
inline unsigned int size() const { return 4; }
inline int32 operator[](unsigned int idx) const
{
int32 temp[4];
store(temp);
return temp[idx];
}
private:
int32x4_t x;
};
#else
......@@ -165,6 +207,8 @@ namespace dlib
return _mm_add_epi32(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_add(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vaddq_s32(lhs, rhs);
#else
return simd4i(lhs[0]+rhs[0],
lhs[1]+rhs[1],
......@@ -183,6 +227,8 @@ namespace dlib
return _mm_sub_epi32(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_sub(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vsubq_s32(lhs, rhs);
#else
return simd4i(lhs[0]-rhs[0],
lhs[1]-rhs[1],
......@@ -210,6 +256,8 @@ namespace dlib
vector int a = lhs(), b = rhs();
asm("vmuluwm %0, %0, %1\n\t" : "+&v" (a) : "v" (b) );
return simd4i(a);
#elif defined(DLIB_HAVE_NEON)
return vmulq_s32(lhs, rhs);
#else
return simd4i(lhs[0]*rhs[0],
lhs[1]*rhs[1],
......@@ -228,6 +276,8 @@ namespace dlib
return _mm_and_si128(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_and(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vandq_s32(lhs, rhs);
#else
return simd4i(lhs[0]&rhs[0],
lhs[1]&rhs[1],
......@@ -246,6 +296,8 @@ namespace dlib
return _mm_or_si128(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_or(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vorrq_s32(lhs, rhs);
#else
return simd4i(lhs[0]|rhs[0],
lhs[1]|rhs[1],
......@@ -264,6 +316,8 @@ namespace dlib
return _mm_xor_si128(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_xor(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return veorq_s32(lhs, rhs);
#else
return simd4i(lhs[0]^rhs[0],
lhs[1]^rhs[1],
......@@ -282,6 +336,8 @@ namespace dlib
return _mm_xor_si128(lhs, _mm_set1_epi32(0xFFFFFFFF));
#elif defined(DLIB_HAVE_VSX)
return vec_xor(lhs(), vec_splats(~0));
#elif defined(DLIB_HAVE_NEON)
return vmvnq_s32(lhs);
#else
return simd4i(~lhs[0],
~lhs[1],
......@@ -298,6 +354,8 @@ namespace dlib
return _mm_sll_epi32(lhs,_mm_cvtsi32_si128(rhs));
#elif defined(DLIB_HAVE_VSX)
return vec_sl(lhs(), vec_splats((uint32_t)rhs));
#elif defined(DLIB_HAVE_NEON)
return vshlq_s32(lhs, simd4i(rhs));
#else
return simd4i(lhs[0]<<rhs,
lhs[1]<<rhs,
......@@ -316,6 +374,12 @@ namespace dlib
return _mm_sra_epi32(lhs,_mm_cvtsi32_si128(rhs));
#elif defined(DLIB_HAVE_VSX)
return vec_sr(lhs(), vec_splats((uint32_t)rhs));
#elif defined(DLIB_HAVE_NEON)
int32 _lhs[4]; lhs.store(_lhs);
return simd4i(_lhs[0]>>rhs,
_lhs[1]>>rhs,
_lhs[2]>>rhs,
_lhs[3]>>rhs);
#else
return simd4i(lhs[0]>>rhs,
lhs[1]>>rhs,
......@@ -334,6 +398,8 @@ namespace dlib
return _mm_cmpeq_epi32(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_cmpeq(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return (int32x4_t)vceqq_s32(lhs,rhs);
#else
return simd4i(lhs[0]==rhs[0] ? 0xFFFFFFFF : 0,
lhs[1]==rhs[1] ? 0xFFFFFFFF : 0,
......@@ -346,7 +412,7 @@ namespace dlib
inline simd4i operator!= (const simd4i& lhs, const simd4i& rhs)
{
#if defined(DLIB_HAVE_SSE2) || defined(DLIB_HAVE_VSX)
#if defined(DLIB_HAVE_SSE2) || defined(DLIB_HAVE_VSX) || defined(DLIB_HAVE_NEON)
return ~(lhs==rhs);
#else
return simd4i(lhs[0]!=rhs[0] ? 0xFFFFFFFF : 0,
......@@ -364,6 +430,8 @@ namespace dlib
return _mm_cmplt_epi32(lhs, rhs);
#elif defined(DLIB_HAVE_VSX)
return vec_cmplt(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return (int32x4_t)vcltq_s32(lhs, rhs);
#else
return simd4i(lhs[0]<rhs[0] ? 0xFFFFFFFF : 0,
lhs[1]<rhs[1] ? 0xFFFFFFFF : 0,
......@@ -385,6 +453,8 @@ namespace dlib
{
#ifdef DLIB_HAVE_SSE2
return ~(lhs > rhs);
#elif defined(DLIB_HAVE_NEON)
return (int32x4_t)vcleq_s32(lhs, rhs);
#else
return simd4i(lhs[0]<=rhs[0] ? 0xFFFFFFFF : 0,
lhs[1]<=rhs[1] ? 0xFFFFFFFF : 0,
......@@ -415,6 +485,8 @@ namespace dlib
std::min(_lhs[3],_rhs[3]));
#elif defined(DLIB_HAVE_VSX)
return vec_min(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return (int32x4_t)vminq_s32(lhs, rhs);
#else
return simd4i(std::min(lhs[0],rhs[0]),
std::min(lhs[1],rhs[1]),
......@@ -438,6 +510,8 @@ namespace dlib
std::max(_lhs[3],_rhs[3]));
#elif defined(DLIB_HAVE_VSX)
return vec_max(lhs(), rhs());
#elif defined(DLIB_HAVE_NEON)
return vmaxq_s32(lhs, rhs);
#else
return simd4i(std::max(lhs[0],rhs[0]),
std::max(lhs[1],rhs[1]),
......@@ -458,6 +532,9 @@ namespace dlib
int32 temp[4];
item.store(temp);
return temp[0]+temp[1]+temp[2]+temp[3];
#elif defined(DLIB_HAVE_NEON)
int32x2_t r = vadd_s32(vget_high_s32(item), vget_low_s32(item));
return vget_lane_s32(vpadd_s32(r, r), 0);
#else
return item[0]+item[1]+item[2]+item[3];
#endif
......@@ -474,6 +551,8 @@ namespace dlib
return ((cmp&a) | _mm_andnot_si128(cmp,b));
#elif defined(DLIB_HAVE_VSX)
return vec_sel(b(), a(), cmp.to_bool());
#elif defined(DLIB_HAVE_NEON)
return vbslq_s32(cmp, a, b);
#else
return ((cmp&a) | (~cmp&b));
#endif
......
......@@ -66,7 +66,11 @@
#define DLIB_HAVE_POWER_VEC
#endif
#endif
#ifdef __ARM_NEON
#ifndef DLIB_HAVE_NEON
#define DLIB_HAVE_NEON
#endif
#endif
#endif
#endif
......@@ -97,7 +101,9 @@
#include <immintrin.h> // AVX
// #include <avx2intrin.h>
#endif
#ifdef DLIB_HAVE_NEON
#include <arm_neon.h> // ARM NEON
#endif
#endif // DLIB_SIMd_CHECK_Hh_
......
......@@ -3,9 +3,21 @@
#ifndef DLIB_SMART_POINTERs_H_
#define DLIB_SMART_POINTERs_H_
#include "smart_pointers/scoped_ptr.h"
// This is legacy smart pointer code that will likely to stop working under default
// compiler flags when C++17 becomes the default standard in the compilers.
// Please consider migrating your code to contemporary smart pointers from C++
// standard library. The warning below will help to detect if the deprecated code
// was included from library's clients.
#if (defined(__GNUC__) && ((__GNUC__ >= 4 && __GNUC_MINOR__ >= 8) || (__GNUC__ > 4))) || \
(defined(__clang__) && ((__clang_major__ >= 3 && __clang_minor__ >= 4)))
#pragma GCC warning "smart_pointers.h is included which will fail to compile under C++17"
#endif
#include <memory>
#include "smart_pointers/shared_ptr.h"
#include "smart_pointers/weak_ptr.h"
#include "smart_pointers/scoped_ptr.h"
#endif // DLIB_SMART_POINTERs_H_
......
// Copyright (C) 2007 Davis E. King (davis@dlib.net)
// License: Boost Software License See LICENSE.txt for the full license.
#ifndef DLIB_SCOPED_PTr_
#define DLIB_SCOPED_PTr_
#ifndef DLIB_SCOPED_PTr_H_
#define DLIB_SCOPED_PTr_H_
#include <algorithm>
#include "../noncopyable.h"
#include "../algs.h"
#include "scoped_ptr_abstract.h"
#include <memory>
namespace dlib
{
// ----------------------------------------------------------------------------------------
template <typename T>
struct default_deleter
{
void operator() (T* item) const
{
delete item;
}
};
template <typename T>
struct default_deleter<T[]>
{
void operator() (T* item) const
{
delete [] item;
}
};
// ----------------------------------------------------------------------------------------
template <
typename T,
typename deleter = default_deleter<T>
>
class scoped_ptr : noncopyable
{
/*!
CONVENTION
- get() == ptr
!*/
public:
typedef T element_type;
typedef deleter deleter_type;
explicit scoped_ptr (
T* p = 0
) : ptr(p) { }
~scoped_ptr()
{
if (ptr)
{
deleter del;
del(ptr);
}
}
void reset (
T* p = 0
)
{
if (ptr)
{
deleter del;
del(ptr);
}
ptr = p;
}
T& operator*() const
{
DLIB_ASSERT(get() != 0,
"\tscoped_ptr::operator*()"
<< "\n\tget() can't be null if you are going to dereference it"
<< "\n\tthis: " << this
);
return *ptr;
}
T* operator->() const
{
DLIB_ASSERT(get() != 0,
"\tscoped_ptr::operator*()"
<< "\n\tget() can't be null"
<< "\n\tthis: " << this
);
return ptr;
}
T* get() const
{
return ptr;
}
operator bool() const
{
return (ptr != 0);
}
void swap(
scoped_ptr& b
)
{
std::swap(ptr,b.ptr);
}
private:
T* ptr;
};
// ----------------------------------------------------------------------------------------
template <
typename T,
typename deleter
>
class scoped_ptr<T[],deleter> : noncopyable
{
/*!
CONVENTION
- get() == ptr
!*/
public:
typedef T element_type;
explicit scoped_ptr (
T* p = 0
) : ptr(p) { }
~scoped_ptr()
{
if (ptr)
{
deleter del;
del(ptr);
}
}
void reset (
T* p = 0
)
{
if (ptr)
{
deleter del;
del(ptr);
}
ptr = p;
}
T& operator[] (
unsigned long idx
) const
{
DLIB_ASSERT(get() != 0,
"\tscoped_ptr::operator[]()"
<< "\n\tget() can't be null if you are going to dereference it"
<< "\n\tthis: " << this
);
return ptr[idx];
}
T* get() const
{
return ptr;
}
operator bool() const
{
return (ptr != 0);
}
void swap(
scoped_ptr& b
)
{
std::swap(ptr,b.ptr);
}
private:
T* ptr;
};
// ----------------------------------------------------------------------------------------
template <
typename T,
typename deleter
>
void swap(
scoped_ptr<T,deleter>& a,
scoped_ptr<T,deleter>& b
)
{
a.swap(b);
}
// ----------------------------------------------------------------------------------------
namespace dlib {
// Template alias for compatibility with clients using old dlib::scoped_ptr
// Old scoped_ptr implementation is removed completely
// This alias may fail in some reference deduction cases
template <class T, class Deleter = std::default_delete<T> >
using scoped_ptr = std::unique_ptr<T, Deleter>;
}
#endif // DLIB_SCOPED_PTr_
#endif
// Copyright (C) 2007 Davis E. King (davis@dlib.net)
// License: Boost Software License See LICENSE.txt for the full license.
#undef DLIB_SCOPED_PTr_ABSTRACT_
#ifdef DLIB_SCOPED_PTr_ABSTRACT_
#include "../noncopyable.h"
namespace dlib
{
// ----------------------------------------------------------------------------------------
template <typename T>
struct default_deleter
{
void operator() (
T* item
) const;
/*!
ensures
- if (T is an array type (e.g. int[])) then
- performs "delete [] item;"
- else
- performs "delete item;"
!*/
};
// ----------------------------------------------------------------------------------------
template <
typename T,
typename deleter = default_deleter<T>
>
class scoped_ptr : noncopyable
{
/*!
REQUIREMENTS ON deleter
Must be a function object that performs deallocation of a pointer
of type T. For example, see the default_deleter type defined above.
It must also not throw when constructed or when performing a delete.
INITIAL VALUE
defined by constructor
WHAT THIS OBJECT REPRESENTS
This is a smart pointer class inspired by the implementation of the scoped_ptr
class found in the Boost C++ library. So this is a simple smart pointer
class which guarantees that the pointer contained within it will always be
deleted.
The class does not permit copying and so does not do any kind of
reference counting. Thus it is very simply and quite fast.
Note that this class allows you to use pointers to arrays as well as
pointers to single items. To let it know that it is supposed to point
to an array you have to declare it using the bracket syntax. Consider
the following examples:
// This is how you make a scoped pointer to a single thing
scoped_ptr<int> single_item(new int);
// This is how you can use a scoped pointer to contain array pointers.
// Note the use of []. This ensures that the proper version of delete
// is called.
scoped_ptr<int[]> array_of_ints(new int[50]);
!*/
public:
typedef T element_type;
typedef deleter deleter_type;
explicit scoped_ptr (
T* p = 0
);
/*!
ensures
- #get() == p
!*/
~scoped_ptr(
);
/*!
ensures
- if (get() != 0) then
- calls deleter()(get())
(i.e. uses the deleter type to delete the pointer that is
contained in this scoped pointer)
!*/
void reset (
T* p = 0
);
/*!
ensures
- if (get() != 0) then
- calls deleter()(get())
(i.e. uses the deleter type to delete the pointer that is
contained in this scoped pointer)
- #get() == p
(i.e. makes this object contain a pointer to p instead of whatever it
used to contain)
!*/
T& operator*(
) const;
/*!
requires
- get() != 0
- T is NOT an array type (e.g. not int[])
ensures
- returns a reference to *get()
!*/
T* operator->(
) const;
/*!
requires
- get() != 0
- T is NOT an array type (e.g. not int[])
ensures
- returns the pointer contained in this object
!*/
T& operator[](
unsigned long idx
) const;
/*!
requires
- get() != 0
- T is an array type (e.g. int[])
ensures
- returns get()[idx]
!*/
T* get(
) const;
/*!
ensures
- returns the pointer contained in this object
!*/
operator bool(
) const;
/*!
ensures
- returns get() != 0
!*/
void swap(
scoped_ptr& b
);
/*!
ensures
- swaps *this and item
!*/
};
template <
typename T
>
void swap(
scoped_ptr<T>& a,
scoped_ptr<T>& b
) { a.swap(b); }
/*!
provides a global swap function
!*/
}
#endif // DLIB_SCOPED_PTr_ABSTRACT_
......@@ -3,6 +3,16 @@
#ifndef DLIB_SMART_POINTERs_THREAD_SAFE_H_
#define DLIB_SMART_POINTERs_THREAD_SAFE_H_
// This is legacy smart pointer code that will likely to stop working under default
// compiler flags when C++17 becomes the default standard in the compilers.
// Please consider migrating your code to contemporary smart pointers from C++
// standard library. The warning below will help to detect if the deprecated code
// was included from library's clients.
#if (defined(__GNUC__) && ((__GNUC__ >= 4 && __GNUC_MINOR__ >= 8) || (__GNUC__ > 4))) || \
(defined(__clang__) && ((__clang_major__ >= 3 && __clang_minor__ >= 4)))
#pragma GCC warning "smart_pointers_thread_safe.h is included which will fail to compile under C++17"
#endif
#include "smart_pointers/shared_ptr_thread_safe.h"
#endif // DLIB_SMART_POINTERs_THREAD_SAFE_H_
......
......@@ -294,14 +294,14 @@ namespace dlib
unsigned long timeout
)
{
scoped_ptr<connection> ptr(con);
std::unique_ptr<connection> ptr(con);
close_gracefully(ptr,timeout);
}
// ----------------------------------------------------------------------------------------
void close_gracefully (
scoped_ptr<connection>& con,
std::unique_ptr<connection>& con,
unsigned long timeout
)
{
......
......@@ -3,11 +3,14 @@
#ifndef DLIB_SOCKETS_EXTENSIONs_
#define DLIB_SOCKETS_EXTENSIONs_
#include <iosfwd>
#include <memory>
#include <string>
#include "../sockets.h"
#include "../smart_pointers/scoped_ptr.h"
#include "sockets_extensions_abstract.h"
#include "../smart_pointers.h"
#include <iosfwd>
namespace dlib
{
......@@ -132,7 +135,7 @@ namespace dlib
// ----------------------------------------------------------------------------------------
void close_gracefully (
scoped_ptr<connection>& con,
std::unique_ptr<connection>& con,
unsigned long timeout = 500
);
......
......@@ -3,9 +3,10 @@
#undef DLIB_SOCKETS_EXTENSIONs_ABSTRACT_
#ifdef DLIB_SOCKETS_EXTENSIONs_ABSTRACT_
#include <memory>
#include <string>
#include "sockets_kernel_abstract.h"
#include "../smart_pointers.h"
#include "../error.h"
namespace dlib
......@@ -265,7 +266,7 @@ namespace dlib
// ----------------------------------------------------------------------------------------
void close_gracefully (
scoped_ptr<connection>& con,
std::unique_ptr<connection>& con,
unsigned long timeout = 500
);
/*!
......
......@@ -498,7 +498,7 @@ namespace dlib
int listener::
accept (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned long timeout
)
{
......@@ -646,7 +646,7 @@ namespace dlib
// ----------------------------------------------------------------------------------------
int create_listener (
scoped_ptr<listener>& new_listener,
std::unique_ptr<listener>& new_listener,
unsigned short port,
const std::string& ip
)
......@@ -764,7 +764,7 @@ namespace dlib
// ----------------------------------------------------------------------------------------
int create_connection (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned short foreign_port,
const std::string& foreign_ip,
unsigned short local_port,
......
......@@ -9,10 +9,11 @@
#include "sockets_kernel_abstract.h"
#include "../algs.h"
#include <memory>
#include <string>
#include "../algs.h"
#include "../threads.h"
#include "../smart_pointers.h"
#include "../uintn.h"
......@@ -269,7 +270,7 @@ namespace dlib
);
int accept (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned long timeout = 0
);
......@@ -324,13 +325,13 @@ namespace dlib
);
int create_listener (
scoped_ptr<listener>& new_listener,
std::unique_ptr<listener>& new_listener,
unsigned short port,
const std::string& ip = ""
);
int create_connection (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned short foreign_port,
const std::string& foreign_ip,
unsigned short local_port = 0,
......
......@@ -527,7 +527,7 @@ namespace dlib
int listener::
accept (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned long timeout
)
{
......@@ -788,7 +788,7 @@ namespace dlib
// ----------------------------------------------------------------------------------------
int create_listener (
scoped_ptr<listener>& new_listener,
std::unique_ptr<listener>& new_listener,
unsigned short port,
const std::string& ip
)
......@@ -907,7 +907,7 @@ namespace dlib
// ----------------------------------------------------------------------------------------
int create_connection (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned short foreign_port,
const std::string& foreign_ip,
unsigned short local_port,
......
......@@ -13,10 +13,14 @@
#define _BSD_SOCKLEN_T_
#include <ctime>
#include <memory>
#include <string>
#include <sys/types.h>
#include <sys/socket.h>
#include <errno.h>
#include <ctime>
#ifndef HPUX
#include <sys/select.h>
#endif
......@@ -26,13 +30,12 @@
#include <netdb.h>
#include <unistd.h>
#include <sys/param.h>
#include <string>
#include <netinet/in.h>
#include "../threads.h"
#include "../algs.h"
#include "../smart_pointers.h"
......@@ -312,7 +315,7 @@ namespace dlib
);
int accept (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned long timeout = 0
);
......@@ -368,13 +371,13 @@ namespace dlib
);
int create_listener (
scoped_ptr<listener>& new_listener,
std::unique_ptr<listener>& new_listener,
unsigned short port,
const std::string& ip = ""
);
int create_connection (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned short foreign_port,
const std::string& foreign_ip,
unsigned short local_port = 0,
......
......@@ -117,13 +117,13 @@ namespace dlib
!*/
int create_listener (
scoped_ptr<listener>& new_listener,
std::unique_ptr<listener>& new_listener,
unsigned short port,
const std::string& ip = ""
);
/*!
This function is just an overload of the above function but it gives you a
scoped_ptr smart pointer instead of a C pointer.
std::unique_ptr smart pointer instead of a C pointer.
!*/
int create_connection (
......@@ -154,7 +154,7 @@ namespace dlib
!*/
int create_connection (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned short foreign_port,
const std::string& foreign_ip,
unsigned short local_port = 0,
......@@ -162,7 +162,7 @@ namespace dlib
);
/*!
This function is just an overload of the above function but it gives you a
scoped_ptr smart pointer instead of a C pointer.
std::unique_ptr smart pointer instead of a C pointer.
!*/
// ----------------------------------------------------------------------------------------
......@@ -459,12 +459,12 @@ namespace dlib
!*/
int accept (
scoped_ptr<connection>& new_connection,
std::unique_ptr<connection>& new_connection,
unsigned long timeout = 0
);
/*!
This function is just an overload of the above function but it gives you a
scoped_ptr smart pointer instead of a C pointer.
std::unique_ptr smart pointer instead of a C pointer.
!*/
unsigned short get_listening_port (
......
......@@ -47,7 +47,7 @@ namespace dlib
}
sockstreambuf (
const scoped_ptr<connection>& con_
const std::unique_ptr<connection>& con_
) :
con(*con_),
out_buffer(0),
......
......@@ -4,7 +4,9 @@
#ifdef DLIB_SOCKSTREAMBUF_ABSTRACT_
#include <iosfwd>
#include <memory>
#include <streambuf>
#include "../sockets/sockets_kernel_abstract.h"
namespace dlib
......@@ -60,7 +62,7 @@ namespace dlib
!*/
sockstreambuf (
const scoped_ptr<connection>& con
const std::unique_ptr<connection>& con
);
/*!
requires
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment