📄 sync.h
字号:
class dbThread {
public:
void create(void (thread_proc* f)(void*), void* arg) { f(arg); }
void join() {}
void detach() {}
static int numberOfProcessors() { return 1; }
};
class dbLocalSemaphore {
int count;
public:
void wait(dbMutex&) {
assert (count > 0);
count -= 1;
}
void signal(unsigned inc = 1) {
count += inc;
}
void open(unsigned initValue = 0) {
count = initValue;
}
void close() {}
};
class dbLocalEvent {
bool signaled;
public:
void wait(dbMutex&) {
assert(signaled);
}
void signal() {
signaled = true;
}
void reset() {
signaled = false;
}
void open(bool initValue = false) {
signaled = initValue;
}
void close() {}
};
template<class T>
class dbThreadContext {
T* value;
public:
T* get() {
return value;
}
void set(T* value) {
this->value = value;
}
dbThreadContext() { value = NULL; }
};
class dbProcessId {
int pid;
public:
bool operator != (dbProcessId const& other) const {
return pid != other.pid;
}
void clear() {
pid = 0;
}
static dbProcessId getCurrent() {
dbProcessId curr;
curr.pid = getpid();
return curr;
}
};
#endif
#define INFINITE (~0U)
#ifdef USE_POSIX_API
class dbInitializationMutex {
sem_t* sem;
public:
enum initializationStatus {
InitializationError,
AlreadyInitialized,
NotYetInitialized
};
initializationStatus initialize(char const* name) {
initializationStatus status;
char* tmp = NULL;
if (*name != '/') {
tmp = new char[strlen(name)+2];
strcpy(tmp+1, name);
*tmp = '/';
name = tmp;
}
while (true) {
sem = sem_open(name, 0);
if (sem == NULL) {
if (errno == ENOENT) {
sem = sem_open(name, O_CREAT|O_EXCL, 0777, 0);
if (sem != NULL) {
status = NotYetInitialized;
break;
} else if (errno != EEXIST) {
status = InitializationError;
break;
}
} else {
status = InitializationError;
break;
}
} else {
status = (sem_wait(sem) == 0 && sem_post(sem) == 0)
? AlreadyInitialized : InitializationError;
break;
}
}
delete[] tmp;
return status;
}
void done() {
sem_post(sem);
}
bool close() {
sem_close(sem);
return false;
}
void erase() {
close();
}
};
class dbSemaphore {
protected:
sem_t* sem;
public:
void wait() {
int rc = sem_wait(sem);
assert(rc == 0);
}
bool wait(unsigned msec) {
#ifdef POSIX_1003_1d
struct timespec abs_ts;
struct timeval cur_tv;
clock_gettime(CLOCK_REALTIME, &cur_tv);
abs_ts.tv_sec = cur_tv.tv_sec + (msec + tv.tv_usec / 1000) / 1000000;
abs_ts.tv_nsec = (msec + tv.tv_usec / 1000) % 1000000 * 1000;
int rc = sem_timedwait(sem, &abs_ts);
if (rc < 0) {
assert(errno == ETIMEDOUT);
return false;
}
return true;
#else
int rc = sem_wait(sem);
assert(rc == 0);
return true;
#endif
}
void signal(unsigned inc = 1) {
while (--inc > 0) {
sem_post(sem);
}
}
void reset() {
while (sem_trywait(sem) == 0);
}
bool open(char const* name, unsigned initValue = 0) {
char* tmp = NULL;
if (*name != '/') {
tmp = new char[strlen(name)+2];
strcpy(tmp+1, name);
*tmp = '/';
name = tmp;
}
sem = sem_open(name, O_CREAT, 0777, initValue);
delete[] tmp;
return sem != NULL;
}
void close() {
sem_close(sem);
}
void erase() {
close();
}
};
class dbEvent : public dbSemaphore {
public:
void wait() {
dbSemaphore::wait();
sem_post(sem);
}
bool wait(unsigned msec) {
if (dbSemaphore::wait(msec)) {
sem_post(sem);
return true;
}
return false;
}
void signal() {
while (sem_trywait(sem) == 0);
sem_post(sem);
}
void reset() {
while (sem_trywait(sem) == 0);
}
bool open(char const* name, bool signaled = false) {
return dbSemaphore::open(name, (int)signaled);
}
};
template<class T>
class dbSharedObject {
char* name;
T* ptr;
int fd;
public:
dbSharedObject() {
name = NULL;
ptr = NULL;
fd = -1;
}
bool open(char* fileName) {
delete[] name;
name = new char[strlen(fileName) + 1];
strcpy(name, fileName);
fd = ::open(fileName, O_RDWR|O_CREAT, 0777);
if (fd < 0) {
return false;
}
ptr = (T*)mmap(NULL,
DOALIGN(sizeof(T), 4096),
PROT_READ|PROT_WRITE,
MAP_SHARED,
fd,
0);
if (ptr == MAP_FAILED) {
ptr = NULL;
::close(fd);
return false;
}
return true;
}
T* get() { return ptr; }
void close() {
if (ptr != NULL) {
munmap(ptr, DOALIGN(sizeof(T), 4096));
}
if (fd > 0) {
::close(fd);
}
}
void erase() {
close();
unlink(name);
name = NULL;
}
~dbSharedObject() {
delete[] name;
}
};
#else // USE_POSIX_API
extern char const* keyFileDir; // default value: "/tmp/"
class dbInitializationMutex {
int semid;
public:
enum initializationStatus {
InitializationError,
AlreadyInitialized,
NotYetInitialized
};
initializationStatus initialize(char const* name);
void done();
bool close();
void erase();
};
class dbSemaphore {
int s;
public:
bool wait(unsigned msec = INFINITE);
void signal(unsigned inc = 1);
bool open(char const* name, unsigned initValue = 0);
void reset();
void close();
void erase();
};
class dbEvent {
int e;
public:
bool wait(unsigned msec = INFINITE);
void signal();
void reset();
bool open(char const* name, bool signaled = false);
void close();
void erase();
};
template<class T>
class dbSharedObject {
T* ptr;
int shm;
public:
bool open(char* name) {
char* fileName = name;
if (*name != '/') {
fileName = new char[strlen(name)+strlen(keyFileDir)+1];
sprintf(fileName, "%s%s", keyFileDir, name);
}
int fd = ::open(fileName, O_RDWR|O_CREAT, 0777);
if (fd < 0) {
if (fileName != name) {
delete[] fileName;
}
return false;
}
::close(fd);
int key = ftok(fileName, '0');
if (fileName != name) {
delete[] fileName;
}
if (key < 0) {
return false;
}
shm = shmget(key, DOALIGN(sizeof(T), 4096), IPC_CREAT|0777);
if (shm < 0) {
return false;
}
ptr = (T*)shmat(shm, NULL, 0);
return (ptr != (T*)-1);
}
T* get() { return ptr; }
void close() {
shmdt((char*)ptr);
}
void erase() {
close();
shmctl(shm, IPC_RMID, NULL);
}
};
#endif
#if defined(__QNX__)
typedef pthread_mutext_t sharedsem_t;
class dbGlobalCriticalSection {
pthread_mutexattr_t attr;
sharedsem_t* sem;
public:
void enter() {
int rc = pthread_mutex_lock(sem);
assert(rc == 0);
}
void leave() {
int rc = pthread_mutex_unlock(sem);
assert(rc == 0);
}
bool open(char const*, sharedsem_t* shr) {
sem = shr;
return true;
}
bool create(char const*, sharedsem_t* shr) {
sem = shr;
pthread_mutexattr_init(&attr);
pthread_mutexattr_setpshared(&attr, PTHREAD_PROCESS_SHARED);
pthread_mutexattr_setrecursive(&attr, PTHREAD_RECURSIVE_ENABLE);
pthread_mutex_init(sem, &attr);
return true;
}
void close() {}
void erase() {
pthread_mutex_destroy(sem);
}
};
#elif defined(__osf__)
#include <errno.h>
typedef msemaphore sharedsem_t;
class dbGlobalCriticalSection {
sharedsem_t* sem;
public:
void enter() {
int rc;
while ((rc = msem_lock(sem, 0)) < 0 && errno == EINTR);
assert(rc == 0);
}
void leave() {
int rc = msem_unlock(sem, 0);
assert(rc == 0);
}
bool open(char const*, sharedsem_t* shr) {
sem = shr;
return true;
}
bool create(char const*, sharedsem_t* shr) {
sem = shr;
msem_init(shr, MSEM_UNLOCKED);
return true;
}
void close() {}
void erase() {
msem_remove(sem);
}
};
#elif defined(__sun)
#include <synch.h>
#include <errno.h>
typedef sema_t sharedsem_t;
class dbGlobalCriticalSection {
sharedsem_t* sem;
public:
void enter() {
int rc;
while ((rc = sema_wait(sem)) < 0 && errno == EINTR);
assert(rc == 0);
}
void leave() {
int rc = sema_post(sem);
assert(rc == 0);
}
bool open(char const*, sharedsem_t* shr) {
sem = shr;
return true;
}
bool create(char const*, sharedsem_t* shr) {
sem = shr;
return sema_init(shr, 1, USYNC_PROCESS, NULL) == 0;
}
void close() {}
void erase() {
sema_destroy(sem);
}
};
#elif defined(USE_POSIX_API)
typedef sem_t sharedsem_t;
class dbGlobalCriticalSection {
sharedsem_t* sem;
public:
void enter() {
int rc = sem_wait(sem);
assert(rc == 0);
}
void leave() {
int rc = sem_post(sem);
assert(rc == 0);
}
bool open(char const* name, sharedsem_t* shr) {
sem = shr;
return true;
}
bool create(char const* name, sharedsem_t* shr) {
sem = shr;
return sem_init(sem, 1, 1) == 0;
}
void close() {}
void erase() {
sem_destroy(sem);
}
};
#else
typedef long sharedsem_t;
class dbGlobalCriticalSection {
int semid;
sharedsem_t* count;
public:
void enter();
void leave();
bool open(char const* name, sharedsem_t* shr);
bool create(char const* name, sharedsem_t* shr);
void close() {}
void erase();
};
#endif
#endif
class FASTDB_DLL_ENTRY dbCriticalSection {
private:
dbMutex& mutex;
public:
dbCriticalSection(dbMutex& guard) : mutex(guard) {
mutex.lock();
}
~dbCriticalSection() {
mutex.unlock();
}
};
#define SMALL_BUF_SIZE 1024
class FASTDB_DLL_ENTRY dbSmallBuffer {
protected:
char* buf;
char smallBuf[SMALL_BUF_SIZE];
public:
dbSmallBuffer(size_t size) {
if (size > SMALL_BUF_SIZE) {
buf = new char[size];
} else {
buf = smallBuf;
}
}
operator char*() { return buf; }
char* base() { return buf; }
~dbSmallBuffer() {
if (buf != smallBuf) {
delete[] buf;
}
}
};
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -