Skip to content

Commit e4689bc

Browse files
[CDRIVER-5607] Clean up OID init to avoid a suspicious time_t trunc (#1643)
* Clean up OID init to avoid a suspicious time_t trunc Instead of doing a clever memcpy of a BE-encoded bunch-of-bits uint32_t, explicitly perform the encoding inline. Avoids a suspicious truncation of time_t to uint32_t, and explains why we are doing it.
1 parent dc85e9b commit e4689bc

File tree

1 file changed

+25
-21
lines changed

1 file changed

+25
-21
lines changed

src/libbson/src/bson/bson-oid.c

Lines changed: 25 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,10 @@
1818

1919
#include <limits.h>
2020
#include <stdarg.h>
21+
#include <stdbool.h>
2122
#include <stdlib.h>
2223
#include <string.h>
24+
#include <stdint.h>
2325

2426
#include <bson/bson-context-private.h>
2527
#include <bson/bson-oid.h>
@@ -74,39 +76,41 @@ BSON_MAYBE_UNUSED static const uint16_t gHexCharPairs[] = {
7476
#endif
7577
};
7678

77-
78-
void
79-
bson_oid_init_sequence (bson_oid_t *oid, /* OUT */
80-
bson_context_t *context) /* IN */
79+
static inline void
80+
_oid_init (bson_oid_t *oid, bson_context_t *context, bool add_random)
8181
{
82-
uint32_t now = (uint32_t) (time (NULL));
83-
82+
BSON_ASSERT (oid);
8483
if (!context) {
8584
context = bson_context_get_default ();
8685
}
8786

88-
now = BSON_UINT32_TO_BE (now);
89-
memcpy (&oid->bytes[0], &now, sizeof (now));
90-
_bson_context_set_oid_seq64 (context, oid);
87+
const time_t now = time (NULL);
88+
// Big-endian encode the low 32 bits of the time as the leading 32 bits of the new OID
89+
oid->bytes[0] = (uint8_t) (now >> 24);
90+
oid->bytes[1] = (uint8_t) (now >> 16);
91+
oid->bytes[2] = (uint8_t) (now >> 8);
92+
oid->bytes[3] = (uint8_t) (now >> 0);
93+
// Maybe add randomness if the caller wants it
94+
if (add_random) {
95+
_bson_context_set_oid_rand (context, oid);
96+
_bson_context_set_oid_seq32 (context, oid);
97+
} else {
98+
_bson_context_set_oid_seq64 (context, oid);
99+
}
91100
}
92101

102+
void
103+
bson_oid_init_sequence (bson_oid_t *oid, /* OUT */
104+
bson_context_t *context) /* IN */
105+
{
106+
_oid_init (oid, context, false /* no randomness */);
107+
}
93108

94109
void
95110
bson_oid_init (bson_oid_t *oid, /* OUT */
96111
bson_context_t *context) /* IN */
97112
{
98-
uint32_t now = (uint32_t) (time (NULL));
99-
100-
BSON_ASSERT (oid);
101-
102-
if (!context) {
103-
context = bson_context_get_default ();
104-
}
105-
106-
now = BSON_UINT32_TO_BE (now);
107-
memcpy (&oid->bytes[0], &now, sizeof (now));
108-
_bson_context_set_oid_rand (context, oid);
109-
_bson_context_set_oid_seq32 (context, oid);
113+
_oid_init (oid, context, true /* add randomness */);
110114
}
111115

112116

0 commit comments

Comments
 (0)