1
0
mirror of synced 2025-11-06 03:20:55 +08:00
Files
SnowFlake-IdGenerator/C/source/idgen/IdGenerator.c
AuroraTea 2da2aa8b4b fix: compatibility of C and C++
// fix: move .h to .c for cpp
// static IdGenerator *_idGenerator = NULL;
2023-01-23 17:35:48 +08:00

158 lines
4.2 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/*
* 版权属于yitter(yitter@126.com)
* 开源地址https://github.com/yitter/idgenerator
*/
#include <stdio.h>
#include <malloc.h>
#include <pthread.h>
#include <errno.h>
#include <unistd.h>
#include "IdGenerator.h"
static IdGenerator *_idGenerator = NULL;
static inline uint64_t WorkerM1Id()
{
return WorkerM1NextId(_idGenerator->Worker);
}
static inline uint64_t WorkerM2Id()
{
return WorkerM2NextId(_idGenerator->Worker);
}
extern IdGenerator *GetIdGenInstance()
{
if (_idGenerator != NULL)
return _idGenerator;
else
{
_idGenerator = (IdGenerator *)malloc(sizeof(IdGenerator));
_idGenerator->Worker = NewSnowFlakeWorker();
return _idGenerator;
}
}
extern void SetOptions(IdGeneratorOptions options)
{
if (GetIdGenInstance() == NULL)
{
exit(1);
}
// 1.BaseTime
if (options.BaseTime == 0)
{
_idGenerator->Worker->BaseTime = 1582136402000;
}
else if (options.BaseTime < 631123200000 || options.BaseTime > GetCurrentTime())
{
perror("BaseTime error.");
exit(1);
}
else
{
_idGenerator->Worker->BaseTime = options.BaseTime;
}
// 2.WorkerIdBitLength
if (options.WorkerIdBitLength <= 0)
{
perror("WorkerIdBitLength error.(range:[1, 21])");
exit(1);
}
if (options.SeqBitLength + options.WorkerIdBitLength > 22)
{
perror("errorWorkerIdBitLength + SeqBitLength <= 22");
exit(1);
}
else
{
// _idGenerator->Worker->WorkerIdBitLength = options.WorkerIdBitLength;
_idGenerator->Worker->WorkerIdBitLength = options.WorkerIdBitLength <= 0 ? 6 : options.WorkerIdBitLength;
}
// 3.WorkerId
uint32_t maxWorkerIdNumber = (1 << options.WorkerIdBitLength) - 1;
if (maxWorkerIdNumber == 0)
{
maxWorkerIdNumber = 63;
}
if (options.WorkerId < 0 || options.WorkerId > maxWorkerIdNumber)
{
perror("WorkerId error. (range:[0, {2^options.WorkerIdBitLength-1]}");
exit(1);
}
else
{
_idGenerator->Worker->WorkerId = options.WorkerId;
}
// 4.SeqBitLength
if (options.SeqBitLength < 2 || options.SeqBitLength > 21)
{
perror("SeqBitLength error. (range:[2, 21])");
exit(1);
}
else
{
// _idGenerator->Worker->SeqBitLength = options.SeqBitLength;
_idGenerator->Worker->SeqBitLength = options.SeqBitLength <= 0 ? 6 : options.SeqBitLength;
}
// 5.MaxSeqNumber
uint32_t maxSeqNumber = (1 << options.SeqBitLength) - 1;
if (maxSeqNumber == 0)
{
maxSeqNumber = 63;
}
if (options.MaxSeqNumber > maxSeqNumber)
{
perror("MaxSeqNumber error. (range:[1, {2^options.SeqBitLength-1}]");
exit(1);
}
else
{
_idGenerator->Worker->MaxSeqNumber = options.MaxSeqNumber <= 0 ? maxSeqNumber : options.MaxSeqNumber;
}
// 6.MinSeqNumber
if (options.MinSeqNumber < 5 || options.MinSeqNumber > maxSeqNumber)
{
perror("MinSeqNumber error. (range:[5, {options.MinSeqNumber}]");
exit(1);
}
else
{
_idGenerator->Worker->MinSeqNumber = options.MinSeqNumber <= 0 ? 5 : options.MinSeqNumber;
}
// 7.TopOverCostCount
if (options.TopOverCostCount < 0 || options.TopOverCostCount > 10000)
{
perror("TopOverCostCount error. (range:[0, 10000]");
exit(1);
}
else
{
//_idGenerator->Worker->TopOverCostCount = options.TopOverCostCount <= 0 ? 2000 : options.TopOverCostCount;
_idGenerator->Worker->TopOverCostCount = options.TopOverCostCount;
}
// 8.Others
_idGenerator->Worker->_TimestampShift =
_idGenerator->Worker->WorkerIdBitLength + _idGenerator->Worker->SeqBitLength;
_idGenerator->Worker->_CurrentSeqNumber = _idGenerator->Worker->MinSeqNumber;
_idGenerator->Worker->Method = options.Method;
if (options.Method == 2)
{
_idGenerator->NextId = WorkerM2Id;
}
else
{
_idGenerator->NextId = WorkerM1Id;
usleep(500 * 1000); // 暂停500ms
}
}