00001
00002
00003
00004
00005
00011 #ifndef _TOR_UTIL_H
00012 #define _TOR_UTIL_H
00013
00014 #include "orconfig.h"
00015 #include "torint.h"
00016 #include "compat.h"
00017 #include <stdio.h>
00018 #include <stdlib.h>
00019
00020 #ifndef O_BINARY
00021 #define O_BINARY 0
00022 #endif
00023 #ifndef O_TEXT
00024 #define O_TEXT 0
00025 #endif
00026
00027
00028
00029
00030 #ifdef NDEBUG
00031
00032
00033
00034
00035
00036
00037
00038
00039 #error "Sorry; we don't support building with NDEBUG."
00040 #endif
00041
00044 #define tor_assert(expr) STMT_BEGIN \
00045 if (PREDICT_UNLIKELY(!(expr))) { \
00046 log_err(LD_BUG, "%s:%d: %s: Assertion %s failed; aborting.", \
00047 _SHORT_FILE_, __LINE__, __func__, #expr); \
00048 fprintf(stderr,"%s:%d %s: Assertion %s failed; aborting.\n", \
00049 _SHORT_FILE_, __LINE__, __func__, #expr); \
00050 abort(); \
00051 } STMT_END
00052
00053
00054
00055
00056
00057
00058 #ifdef USE_DMALLOC
00059 #define DMALLOC_PARAMS , const char *file, const int line
00060 #define DMALLOC_ARGS , _SHORT_FILE_, __LINE__
00061 #else
00062 #define DMALLOC_PARAMS
00063 #define DMALLOC_ARGS
00064 #endif
00065
00068
00069 #define tor_fragile_assert()
00070
00071
00072 void *_tor_malloc(size_t size DMALLOC_PARAMS) ATTR_MALLOC;
00073 void *_tor_malloc_zero(size_t size DMALLOC_PARAMS) ATTR_MALLOC;
00074 void *_tor_malloc_roundup(size_t *size DMALLOC_PARAMS) ATTR_MALLOC;
00075 void *_tor_realloc(void *ptr, size_t size DMALLOC_PARAMS);
00076 char *_tor_strdup(const char *s DMALLOC_PARAMS) ATTR_MALLOC ATTR_NONNULL((1));
00077 char *_tor_strndup(const char *s, size_t n DMALLOC_PARAMS)
00078 ATTR_MALLOC ATTR_NONNULL((1));
00079 void *_tor_memdup(const void *mem, size_t len DMALLOC_PARAMS)
00080 ATTR_MALLOC ATTR_NONNULL((1));
00081 void _tor_free(void *mem);
00082 #ifdef USE_DMALLOC
00083 extern int dmalloc_free(const char *file, const int line, void *pnt,
00084 const int func_id);
00085 #define tor_free(p) STMT_BEGIN \
00086 if (PREDICT_LIKELY((p)!=NULL)) { \
00087 dmalloc_free(_SHORT_FILE_, __LINE__, (p), 0); \
00088 (p)=NULL; \
00089 } \
00090 STMT_END
00091 #else
00092
00099 #define tor_free(p) STMT_BEGIN \
00100 if (PREDICT_LIKELY((p)!=NULL)) { \
00101 free(p); \
00102 (p)=NULL; \
00103 } \
00104 STMT_END
00105 #endif
00106
00107 #define tor_malloc(size) _tor_malloc(size DMALLOC_ARGS)
00108 #define tor_malloc_zero(size) _tor_malloc_zero(size DMALLOC_ARGS)
00109 #define tor_malloc_roundup(szp) _tor_malloc_roundup(szp DMALLOC_ARGS)
00110 #define tor_realloc(ptr, size) _tor_realloc(ptr, size DMALLOC_ARGS)
00111 #define tor_strdup(s) _tor_strdup(s DMALLOC_ARGS)
00112 #define tor_strndup(s, n) _tor_strndup(s, n DMALLOC_ARGS)
00113 #define tor_memdup(s, n) _tor_memdup(s, n DMALLOC_ARGS)
00114
00115 void tor_log_mallinfo(int severity);
00116
00118 #if defined(__GNUC__) && __GNUC__ > 3
00119 #define STRUCT_OFFSET(tp, member) __builtin_offsetof(tp, member)
00120 #else
00121 #define STRUCT_OFFSET(tp, member) \
00122 ((off_t) (((char*)&((tp*)0)->member)-(char*)0))
00123 #endif
00124
00134 #define STRUCT_VAR_P(st, off) ((void*) ( ((char*)(st)) + (off) ) )
00135
00145 #define SUBTYPE_P(p, subtype, basemember) \
00146 ((void*) ( ((char*)(p)) - STRUCT_OFFSET(subtype, basemember) ))
00147
00148
00150 #define bool_eq(a,b) (!(a)==!(b))
00151
00152 #define bool_neq(a,b) (!(a)!=!(b))
00153
00154
00155 double tor_mathlog(double d) ATTR_CONST;
00156 long tor_lround(double d) ATTR_CONST;
00157 int tor_log2(uint64_t u64) ATTR_CONST;
00158 uint64_t round_to_power_of_2(uint64_t u64);
00159 unsigned round_to_next_multiple_of(unsigned number, unsigned divisor);
00160 uint32_t round_uint32_to_next_multiple_of(uint32_t number, uint32_t divisor);
00161 uint64_t round_uint64_to_next_multiple_of(uint64_t number, uint64_t divisor);
00162
00163
00164
00166 #define HEX_CHARACTERS "0123456789ABCDEFabcdef"
00167 void tor_strlower(char *s) ATTR_NONNULL((1));
00168 void tor_strupper(char *s) ATTR_NONNULL((1));
00169 int tor_strisprint(const char *s) ATTR_PURE ATTR_NONNULL((1));
00170 int tor_strisnonupper(const char *s) ATTR_PURE ATTR_NONNULL((1));
00171 int strcmpstart(const char *s1, const char *s2) ATTR_PURE ATTR_NONNULL((1,2));
00172 int strcmp_len(const char *s1, const char *s2, size_t len)
00173 ATTR_PURE ATTR_NONNULL((1,2));
00174 int strcasecmpstart(const char *s1, const char *s2)
00175 ATTR_PURE ATTR_NONNULL((1,2));
00176 int strcmpend(const char *s1, const char *s2) ATTR_PURE ATTR_NONNULL((1,2));
00177 int strcasecmpend(const char *s1, const char *s2)
00178 ATTR_PURE ATTR_NONNULL((1,2));
00179 int memcmpstart(const void *mem, size_t memlen,
00180 const char *prefix) ATTR_PURE;
00181
00182 void tor_strstrip(char *s, const char *strip) ATTR_NONNULL((1,2));
00183 long tor_parse_long(const char *s, int base, long min,
00184 long max, int *ok, char **next);
00185 unsigned long tor_parse_ulong(const char *s, int base, unsigned long min,
00186 unsigned long max, int *ok, char **next);
00187 double tor_parse_double(const char *s, double min, double max, int *ok,
00188 char **next);
00189 uint64_t tor_parse_uint64(const char *s, int base, uint64_t min,
00190 uint64_t max, int *ok, char **next);
00191 const char *hex_str(const char *from, size_t fromlen) ATTR_NONNULL((1));
00192 const char *eat_whitespace(const char *s) ATTR_PURE;
00193 const char *eat_whitespace_eos(const char *s, const char *eos) ATTR_PURE;
00194 const char *eat_whitespace_no_nl(const char *s) ATTR_PURE;
00195 const char *eat_whitespace_eos_no_nl(const char *s, const char *eos) ATTR_PURE;
00196 const char *find_whitespace(const char *s) ATTR_PURE;
00197 const char *find_whitespace_eos(const char *s, const char *eos) ATTR_PURE;
00198 const char *find_str_at_start_of_line(const char *haystack, const char *needle)
00199 ATTR_PURE;
00200 int tor_mem_is_zero(const char *mem, size_t len) ATTR_PURE;
00201 int tor_digest_is_zero(const char *digest) ATTR_PURE;
00202 int tor_digest256_is_zero(const char *digest) ATTR_PURE;
00203 char *esc_for_log(const char *string) ATTR_MALLOC;
00204 const char *escaped(const char *string);
00205 struct smartlist_t;
00206 void wrap_string(struct smartlist_t *out, const char *string, size_t width,
00207 const char *prefix0, const char *prefixRest);
00208 int tor_vsscanf(const char *buf, const char *pattern, va_list ap);
00209 int tor_sscanf(const char *buf, const char *pattern, ...)
00210 #ifdef __GNUC__
00211 __attribute__((format(scanf, 2, 3)))
00212 #endif
00213 ;
00214
00215 int hex_decode_digit(char c);
00216 void base16_encode(char *dest, size_t destlen, const char *src, size_t srclen);
00217 int base16_decode(char *dest, size_t destlen, const char *src, size_t srclen);
00218
00219
00220 double tv_to_double(const struct timeval *tv);
00221 int64_t tv_to_msec(const struct timeval *tv);
00222 int64_t tv_to_usec(const struct timeval *tv);
00223 long tv_udiff(const struct timeval *start, const struct timeval *end);
00224 long tv_mdiff(const struct timeval *start, const struct timeval *end);
00225 time_t tor_timegm(struct tm *tm);
00226 #define RFC1123_TIME_LEN 29
00227 void format_rfc1123_time(char *buf, time_t t);
00228 int parse_rfc1123_time(const char *buf, time_t *t);
00229 #define ISO_TIME_LEN 19
00230 void format_local_iso_time(char *buf, time_t t);
00231 void format_iso_time(char *buf, time_t t);
00232 int parse_iso_time(const char *buf, time_t *t);
00233 int parse_http_time(const char *buf, struct tm *tm);
00234 int format_time_interval(char *out, size_t out_len, long interval);
00235
00236
00237 #ifdef TIME_IS_FAST
00238 #define approx_time() time(NULL)
00239 #define update_approx_time(t) STMT_NIL
00240 #else
00241 time_t approx_time(void);
00242 void update_approx_time(time_t now);
00243 #endif
00244
00245
00246 void ftime_set_maximum_sloppiness(int seconds);
00247 void ftime_set_estimated_skew(int seconds);
00248
00249
00250 int ftime_maybe_after(time_t now, time_t when);
00251 int ftime_maybe_before(time_t now, time_t when);
00252 int ftime_definitely_after(time_t now, time_t when);
00253 int ftime_definitely_before(time_t now, time_t when);
00254
00255
00256 ssize_t write_all(int fd, const char *buf, size_t count, int isSocket);
00257 ssize_t read_all(int fd, char *buf, size_t count, int isSocket);
00258
00261 typedef enum { FN_ERROR, FN_NOENT, FN_FILE, FN_DIR } file_status_t;
00262 file_status_t file_status(const char *filename);
00263
00266 typedef enum { CPD_NONE, CPD_CREATE, CPD_CHECK } cpd_check_t;
00267 int check_private_dir(const char *dirname, cpd_check_t check);
00268 #define OPEN_FLAGS_REPLACE (O_WRONLY|O_CREAT|O_TRUNC)
00269 #define OPEN_FLAGS_APPEND (O_WRONLY|O_CREAT|O_APPEND)
00270 typedef struct open_file_t open_file_t;
00271 int start_writing_to_file(const char *fname, int open_flags, int mode,
00272 open_file_t **data_out);
00273 FILE *start_writing_to_stdio_file(const char *fname, int open_flags, int mode,
00274 open_file_t **data_out);
00275 FILE *fdopen_file(open_file_t *file_data);
00276 int finish_writing_to_file(open_file_t *file_data);
00277 int abort_writing_to_file(open_file_t *file_data);
00278 int write_str_to_file(const char *fname, const char *str, int bin);
00279 int write_bytes_to_file(const char *fname, const char *str, size_t len,
00280 int bin);
00283 typedef struct sized_chunk_t {
00284 const char *bytes;
00285 size_t len;
00286 } sized_chunk_t;
00287 int write_chunks_to_file(const char *fname, const struct smartlist_t *chunks,
00288 int bin);
00289 int append_bytes_to_file(const char *fname, const char *str, size_t len,
00290 int bin);
00291
00293 #define RFTS_BIN 1
00294
00295 #define RFTS_IGNORE_MISSING 2
00296
00297 struct stat;
00298 char *read_file_to_str(const char *filename, int flags, struct stat *stat_out)
00299 ATTR_MALLOC;
00300 const char *parse_config_line_from_str(const char *line,
00301 char **key_out, char **value_out);
00302 char *expand_filename(const char *filename);
00303 struct smartlist_t *tor_listdir(const char *dirname);
00304 int path_is_relative(const char *filename) ATTR_PURE;
00305
00306
00307 void start_daemon(void);
00308 void finish_daemon(const char *desired_cwd);
00309 void write_pidfile(char *filename);
00310
00311 const char *libor_get_digests(void);
00312
00313 #endif
00314