Google の TrueTime API (Wired、Slashdot など) を複製するのは難しいとマスコミが一般的に言っている理由がわかりません。
Google が達成している低いエラー間隔を取得するのがいかに難しいかは理解できますが、API 自体がどれほど難しいかはわかりません。
たとえば、ハッキングされたバージョンを作成しました。間隔はこちら。
typedef struct TT_interval {
struct timeval earliest;
struct timeval latest;
} TT_interval;
これが now 関数です。
int TT_now(TT_interval* interval)
{
struct ntptimeval tv;
struct timeval delta;
struct timeval* earliest_p = &(interval->earliest);
struct timeval* latest_p = &(interval->latest);
struct timeval* now_p = &(tv.time);
struct timeval* delta_p = δ
timerclear(&delta);
timerclear(&interval->earliest);
timerclear(&interval->latest);
if(ntp_gettime(&tv) == 0) {
tv.maxerror = tv.maxerror > 0 ? tv.maxerror : -(tv.maxerror);
delta.tv_sec = delta.tv_sec + (tv.maxerror / 1000);
delta.tv_usec = delta.tv_usec + ((tv.maxerror % 1000) * 1000);
if(delta.tv_usec > 1000000) {
delta.tv_usec -= 1000000;
delta.tv_sec++;
}
timeradd(now_p, delta_p, latest_p);
timersub(now_p, delta_p, earliest_p);
} else {
printf("error on ntp_gettime. %s\n", strerror(errno));
return ERROR;
}
return SUCCESS;
}
最後に、before 関数と after 関数があります (now 関数のラッパーであり、DRY リファクタリングを少し使用できます)。
int TT_before(TT_interval* interval, bool* success)
{
struct timeval* latest_p;
struct timeval* earliest_p;
TT_interval now;
if(TT_now(&now) != SUCCESS) {
return ERROR;
}
latest_p = &(interval->latest);
earliest_p = &(now.earliest);
if(timercmp(latest_p, earliest_p, <) != 0) {
*success = true;
return SUCCESS;
} else {
*success = false;
return SUCCESS;
}
return ERROR;
}
int TT_after(TT_interval* interval, bool* success)
{
struct timeval* latest_p;
struct timeval* earliest_p;
TT_interval now;
if(TT_now(&now) != SUCCESS) {
return ERROR;
}
earliest_p = &(interval->latest);
latest_p = &(now.earliest);
if(timercmp(latest_p, earliest_p, <) != 0) {
*success = true;
return SUCCESS;
} else {
*success = false;
return SUCCESS;
}
return ERROR;
}
約 5,000us から 350,000us のインターバル エラーが発生しているようです (パブリック NTPd を使用)。これは Google の数字とはかけ離れていますが、どこかから始める必要があります。
精彩を欠いたパフォーマンス以外に、この設計に、Spanner のようなものを上に構築することを妨げる重大な欠陥はありますか?