file.h 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525
  1. /**
  2. * \file libyasm/file.h
  3. * \brief YASM file helpers.
  4. *
  5. * \license
  6. * Copyright (C) 2001-2007 Peter Johnson
  7. *
  8. * Redistribution and use in source and binary forms, with or without
  9. * modification, are permitted provided that the following conditions
  10. * are met:
  11. * - Redistributions of source code must retain the above copyright
  12. * notice, this list of conditions and the following disclaimer.
  13. * - Redistributions in binary form must reproduce the above copyright
  14. * notice, this list of conditions and the following disclaimer in the
  15. * documentation and/or other materials provided with the distribution.
  16. *
  17. * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND OTHER CONTRIBUTORS ``AS IS''
  18. * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  19. * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  20. * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR OTHER CONTRIBUTORS BE
  21. * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
  22. * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
  23. * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
  24. * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
  25. * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
  26. * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  27. * POSSIBILITY OF SUCH DAMAGE.
  28. * \endlicense
  29. */
  30. #ifndef YASM_FILE_H
  31. #define YASM_FILE_H
  32. #ifndef YASM_LIB_DECL
  33. #define YASM_LIB_DECL
  34. #endif
  35. /** Re2c scanner state. */
  36. typedef struct yasm_scanner {
  37. unsigned char *bot; /**< Bottom of scan buffer */
  38. unsigned char *tok; /**< Start of token */
  39. unsigned char *ptr; /**< Scan marker */
  40. unsigned char *cur; /**< Cursor (1 past end of token) */
  41. unsigned char *lim; /**< Limit of good data */
  42. unsigned char *top; /**< Top of scan buffer */
  43. unsigned char *eof; /**< End of file */
  44. } yasm_scanner;
  45. /** Initialize scanner state.
  46. * \param scanner Re2c scanner state
  47. */
  48. YASM_LIB_DECL
  49. void yasm_scanner_initialize(yasm_scanner *scanner);
  50. /** Frees any memory used by scanner state; does not free state itself.
  51. * \param scanner Re2c scanner state
  52. */
  53. YASM_LIB_DECL
  54. void yasm_scanner_delete(yasm_scanner *scanner);
  55. /** Fill a scanner state structure with data coming from an input function.
  56. * \param scanner Re2c scanner state
  57. * \param cursor Re2c scan cursor
  58. * \param input_func Input function to read data; takes buffer and maximum
  59. * number of bytes, returns number of bytes read.
  60. * \param input_func_data Data to pass as the first parameter to input_func
  61. * \return 1 if this was the first time this function was called on this
  62. * scanner state, 0 otherwise.
  63. */
  64. YASM_LIB_DECL
  65. int yasm_fill_helper
  66. (yasm_scanner *scanner, unsigned char **cursor,
  67. size_t (*input_func) (void *d, unsigned char *buf, size_t max),
  68. void *input_func_data);
  69. /** Unescape a string with C-style escapes. Handles b, f, n, r, t, and hex
  70. * and octal escapes. String is updated in-place.
  71. * Edge cases:
  72. * - hex escapes: reads as many hex digits as possible, takes last 2 as value.
  73. * - oct escapes: takes up to 3 digits 0-9 and scales appropriately, with
  74. * warning.
  75. * \param str C-style string (updated in place)
  76. * \param len length of string (updated with new length)
  77. */
  78. YASM_LIB_DECL
  79. void yasm_unescape_cstring(unsigned char *str, size_t *len);
  80. /** Split a UNIX pathname into head (directory) and tail (base filename)
  81. * portions.
  82. * \internal
  83. * \param path pathname
  84. * \param tail (returned) base filename
  85. * \return Length of head (directory).
  86. */
  87. YASM_LIB_DECL
  88. size_t yasm__splitpath_unix(const char *path, /*@out@*/ const char **tail);
  89. /** Split a Windows pathname into head (directory) and tail (base filename)
  90. * portions.
  91. * \internal
  92. * \param path pathname
  93. * \param tail (returned) base filename
  94. * \return Length of head (directory).
  95. */
  96. YASM_LIB_DECL
  97. size_t yasm__splitpath_win(const char *path, /*@out@*/ const char **tail);
  98. /** Split a pathname into head (directory) and tail (base filename) portions.
  99. * Unless otherwise defined, defaults to yasm__splitpath_unix().
  100. * \internal
  101. * \param path pathname
  102. * \param tail (returned) base filename
  103. * \return Length of head (directory).
  104. */
  105. #ifndef yasm__splitpath
  106. # if defined (_WIN32) || defined (WIN32) || defined (__MSDOS__) || \
  107. defined (__DJGPP__) || defined (__OS2__)
  108. # define yasm__splitpath(path, tail) yasm__splitpath_win(path, tail)
  109. # else
  110. # define yasm__splitpath(path, tail) yasm__splitpath_unix(path, tail)
  111. # endif
  112. #endif
  113. /** Get the current working directory.
  114. * \internal
  115. * \return Current working directory pathname (newly allocated).
  116. */
  117. YASM_LIB_DECL
  118. /*@only@*/ char *yasm__getcwd(void);
  119. /** Convert a relative or absolute pathname into an absolute pathname.
  120. * \internal
  121. * \param path pathname
  122. * \return Absolute version of path (newly allocated).
  123. */
  124. YASM_LIB_DECL
  125. /*@only@*/ char *yasm__abspath(const char *path);
  126. /** Build a UNIX pathname that is equivalent to accessing the "to" pathname
  127. * when you're in the directory containing "from". Result is relative if both
  128. * from and to are relative.
  129. * \internal
  130. * \param from from pathname
  131. * \param to to pathname
  132. * \return Combined path (newly allocated).
  133. */
  134. YASM_LIB_DECL
  135. char *yasm__combpath_unix(const char *from, const char *to);
  136. /** Build a Windows pathname that is equivalent to accessing the "to" pathname
  137. * when you're in the directory containing "from". Result is relative if both
  138. * from and to are relative.
  139. * \internal
  140. * \param from from pathname
  141. * \param to to pathname
  142. * \return Combined path (newly allocated).
  143. */
  144. YASM_LIB_DECL
  145. char *yasm__combpath_win(const char *from, const char *to);
  146. /** Build a pathname that is equivalent to accessing the "to" pathname
  147. * when you're in the directory containing "from". Result is relative if both
  148. * from and to are relative.
  149. * Unless otherwise defined, defaults to yasm__combpath_unix().
  150. * \internal
  151. * \param from from pathname
  152. * \param to to pathname
  153. * \return Combined path (newly allocated).
  154. */
  155. #ifndef yasm__combpath
  156. # if defined (_WIN32) || defined (WIN32) || defined (__MSDOS__) || \
  157. defined (__DJGPP__) || defined (__OS2__)
  158. # define yasm__combpath(from, to) yasm__combpath_win(from, to)
  159. # else
  160. # define yasm__combpath(from, to) yasm__combpath_unix(from, to)
  161. # endif
  162. #endif
  163. /** Recursively create tree of directories needed for pathname.
  164. * \internal
  165. * \param path pathname
  166. * \param win handle windows paths
  167. * \return Length of directory portion of pathname.
  168. */
  169. YASM_LIB_DECL
  170. size_t yasm__createpath_common(const char *path, int win);
  171. /** Recursively create tree of directories needed for pathname.
  172. * Unless otherwise defined, defaults to yasm__createpath_unix().
  173. * \internal
  174. * \param path pathname
  175. * \return Length of directory portion of pathname.
  176. */
  177. #ifndef yasm__createpath
  178. # if defined (_WIN32) || defined (WIN32) || defined (__MSDOS__) || \
  179. defined (__DJGPP__) || defined (__OS2__)
  180. # define yasm__createpath(path) yasm__createpath_common(path, 1)
  181. # else
  182. # define yasm__createpath(path) yasm__createpath_common(path, 0)
  183. # endif
  184. #endif
  185. /** Try to find and open an include file, searching through include paths.
  186. * First iname is looked for relative to the directory containing "from", then
  187. * it's looked for relative to each of the include paths.
  188. *
  189. * All pathnames may be either absolute or relative; from, oname, and
  190. * include paths, if relative, are relative from the current working directory.
  191. *
  192. * First match wins; the full pathname (newly allocated) to the opened file
  193. * is saved into oname, and the fopen'ed FILE * is returned. If not found,
  194. * NULL is returned.
  195. *
  196. * \param iname file to include
  197. * \param from file doing the including
  198. * \param mode fopen mode string
  199. * \param oname full pathname of included file (may be relative). NULL
  200. * may be passed if this is unwanted.
  201. * \return fopen'ed include file, or NULL if not found.
  202. */
  203. YASM_LIB_DECL
  204. /*@null@*/ FILE *yasm_fopen_include
  205. (const char *iname, const char *from, const char *mode,
  206. /*@null@*/ /*@out@*/ /*@only@*/ char **oname);
  207. /** Delete any stored include paths added by yasm_add_include_path().
  208. */
  209. YASM_LIB_DECL
  210. void yasm_delete_include_paths(void);
  211. /** Iterate through include paths.
  212. */
  213. YASM_LIB_DECL
  214. const char * yasm_get_include_dir(void **iter);
  215. /** Add an include path for use by yasm_fopen_include().
  216. * If path is relative, it is treated by yasm_fopen_include() as relative to
  217. * the current working directory.
  218. *
  219. * \param path path to add
  220. */
  221. YASM_LIB_DECL
  222. void yasm_add_include_path(const char *path);
  223. /** Write an 8-bit value to a buffer, incrementing buffer pointer.
  224. * \note Only works properly if ptr is an (unsigned char *).
  225. * \param ptr buffer
  226. * \param val 8-bit value
  227. */
  228. #define YASM_WRITE_8(ptr, val) \
  229. *((ptr)++) = (unsigned char)((val) & 0xFF)
  230. /** Write a 16-bit value to a buffer in little endian, incrementing buffer
  231. * pointer.
  232. * \note Only works properly if ptr is an (unsigned char *).
  233. * \param ptr buffer
  234. * \param val 16-bit value
  235. */
  236. #define YASM_WRITE_16_L(ptr, val) \
  237. do { \
  238. *((ptr)++) = (unsigned char)((val) & 0xFF); \
  239. *((ptr)++) = (unsigned char)(((val) >> 8) & 0xFF); \
  240. } while (0)
  241. /** Write a 32-bit value to a buffer in little endian, incrementing buffer
  242. * pointer.
  243. * \note Only works properly if ptr is an (unsigned char *).
  244. * \param ptr buffer
  245. * \param val 32-bit value
  246. */
  247. #define YASM_WRITE_32_L(ptr, val) \
  248. do { \
  249. *((ptr)++) = (unsigned char)((val) & 0xFF); \
  250. *((ptr)++) = (unsigned char)(((val) >> 8) & 0xFF); \
  251. *((ptr)++) = (unsigned char)(((val) >> 16) & 0xFF); \
  252. *((ptr)++) = (unsigned char)(((val) >> 24) & 0xFF); \
  253. } while (0)
  254. /** Write a 16-bit value to a buffer in big endian, incrementing buffer
  255. * pointer.
  256. * \note Only works properly if ptr is an (unsigned char *).
  257. * \param ptr buffer
  258. * \param val 16-bit value
  259. */
  260. #define YASM_WRITE_16_B(ptr, val) \
  261. do { \
  262. *((ptr)++) = (unsigned char)(((val) >> 8) & 0xFF); \
  263. *((ptr)++) = (unsigned char)((val) & 0xFF); \
  264. } while (0)
  265. /** Write a 32-bit value to a buffer in big endian, incrementing buffer
  266. * pointer.
  267. * \note Only works properly if ptr is an (unsigned char *).
  268. * \param ptr buffer
  269. * \param val 32-bit value
  270. */
  271. #define YASM_WRITE_32_B(ptr, val) \
  272. do { \
  273. *((ptr)++) = (unsigned char)(((val) >> 24) & 0xFF); \
  274. *((ptr)++) = (unsigned char)(((val) >> 16) & 0xFF); \
  275. *((ptr)++) = (unsigned char)(((val) >> 8) & 0xFF); \
  276. *((ptr)++) = (unsigned char)((val) & 0xFF); \
  277. } while (0)
  278. /** Write an 8-bit value to a buffer. Does not increment buffer pointer.
  279. * \note Only works properly if ptr is an (unsigned char *).
  280. * \param ptr buffer
  281. * \param val 8-bit value
  282. */
  283. #define YASM_SAVE_8(ptr, val) \
  284. *(ptr) = (unsigned char)((val) & 0xFF)
  285. /** Write a 16-bit value to a buffer in little endian. Does not increment
  286. * buffer pointer.
  287. * \note Only works properly if ptr is an (unsigned char *).
  288. * \param ptr buffer
  289. * \param val 16-bit value
  290. */
  291. #define YASM_SAVE_16_L(ptr, val) \
  292. do { \
  293. *(ptr) = (unsigned char)((val) & 0xFF); \
  294. *((ptr)+1) = (unsigned char)(((val) >> 8) & 0xFF); \
  295. } while (0)
  296. /** Write a 32-bit value to a buffer in little endian. Does not increment
  297. * buffer pointer.
  298. * \note Only works properly if ptr is an (unsigned char *).
  299. * \param ptr buffer
  300. * \param val 32-bit value
  301. */
  302. #define YASM_SAVE_32_L(ptr, val) \
  303. do { \
  304. *(ptr) = (unsigned char)((val) & 0xFF); \
  305. *((ptr)+1) = (unsigned char)(((val) >> 8) & 0xFF); \
  306. *((ptr)+2) = (unsigned char)(((val) >> 16) & 0xFF); \
  307. *((ptr)+3) = (unsigned char)(((val) >> 24) & 0xFF); \
  308. } while (0)
  309. /** Write a 16-bit value to a buffer in big endian. Does not increment buffer
  310. * pointer.
  311. * \note Only works properly if ptr is an (unsigned char *).
  312. * \param ptr buffer
  313. * \param val 16-bit value
  314. */
  315. #define YASM_SAVE_16_B(ptr, val) \
  316. do { \
  317. *(ptr) = (unsigned char)(((val) >> 8) & 0xFF); \
  318. *((ptr)+1) = (unsigned char)((val) & 0xFF); \
  319. } while (0)
  320. /** Write a 32-bit value to a buffer in big endian. Does not increment buffer
  321. * pointer.
  322. * \note Only works properly if ptr is an (unsigned char *).
  323. * \param ptr buffer
  324. * \param val 32-bit value
  325. */
  326. #define YASM_SAVE_32_B(ptr, val) \
  327. do { \
  328. *(ptr) = (unsigned char)(((val) >> 24) & 0xFF); \
  329. *((ptr)+1) = (unsigned char)(((val) >> 16) & 0xFF); \
  330. *((ptr)+2) = (unsigned char)(((val) >> 8) & 0xFF); \
  331. *((ptr)+3) = (unsigned char)((val) & 0xFF); \
  332. } while (0)
  333. /** Direct-to-file version of YASM_SAVE_16_L().
  334. * \note Using the macro multiple times with a single fwrite() call will
  335. * probably be faster than calling this function many times.
  336. * \param val 16-bit value
  337. * \param f file
  338. * \return 1 if the write was successful, 0 if not (just like fwrite()).
  339. */
  340. YASM_LIB_DECL
  341. size_t yasm_fwrite_16_l(unsigned short val, FILE *f);
  342. /** Direct-to-file version of YASM_SAVE_32_L().
  343. * \note Using the macro multiple times with a single fwrite() call will
  344. * probably be faster than calling this function many times.
  345. * \param val 32-bit value
  346. * \param f file
  347. * \return 1 if the write was successful, 0 if not (just like fwrite()).
  348. */
  349. YASM_LIB_DECL
  350. size_t yasm_fwrite_32_l(unsigned long val, FILE *f);
  351. /** Direct-to-file version of YASM_SAVE_16_B().
  352. * \note Using the macro multiple times with a single fwrite() call will
  353. * probably be faster than calling this function many times.
  354. * \param val 16-bit value
  355. * \param f file
  356. * \return 1 if the write was successful, 0 if not (just like fwrite()).
  357. */
  358. YASM_LIB_DECL
  359. size_t yasm_fwrite_16_b(unsigned short val, FILE *f);
  360. /** Direct-to-file version of YASM_SAVE_32_B().
  361. * \note Using the macro multiple times with a single fwrite() call will
  362. * probably be faster than calling this function many times.
  363. * \param val 32-bit value
  364. * \param f file
  365. * \return 1 if the write was successful, 0 if not (just like fwrite()).
  366. */
  367. YASM_LIB_DECL
  368. size_t yasm_fwrite_32_b(unsigned long val, FILE *f);
  369. /** Read an 8-bit value from a buffer, incrementing buffer pointer.
  370. * \note Only works properly if ptr is an (unsigned char *).
  371. * \param ptr buffer
  372. * \param val 8-bit value
  373. */
  374. #define YASM_READ_8(val, ptr) \
  375. (val) = *((ptr)++) & 0xFF
  376. /** Read a 16-bit value from a buffer in little endian, incrementing buffer
  377. * pointer.
  378. * \note Only works properly if ptr is an (unsigned char *).
  379. * \param ptr buffer
  380. * \param val 16-bit value
  381. */
  382. #define YASM_READ_16_L(val, ptr) \
  383. do { \
  384. (val) = *((ptr)++) & 0xFF; \
  385. (val) |= (*((ptr)++) & 0xFF) << 8; \
  386. } while (0)
  387. /** Read a 32-bit value from a buffer in little endian, incrementing buffer
  388. * pointer.
  389. * \note Only works properly if ptr is an (unsigned char *).
  390. * \param ptr buffer
  391. * \param val 32-bit value
  392. */
  393. #define YASM_READ_32_L(val, ptr) \
  394. do { \
  395. (val) = *((ptr)++) & 0xFF; \
  396. (val) |= (*((ptr)++) & 0xFF) << 8; \
  397. (val) |= (*((ptr)++) & 0xFF) << 16; \
  398. (val) |= (*((ptr)++) & 0xFF) << 24; \
  399. } while (0)
  400. /** Read a 16-bit value from a buffer in big endian, incrementing buffer
  401. * pointer.
  402. * \note Only works properly if ptr is an (unsigned char *).
  403. * \param ptr buffer
  404. * \param val 16-bit value
  405. */
  406. #define YASM_READ_16_B(val, ptr) \
  407. do { \
  408. (val) = (*((ptr)++) & 0xFF) << 8; \
  409. (val) |= *((ptr)++) & 0xFF; \
  410. } while (0)
  411. /** Read a 32-bit value from a buffer in big endian, incrementing buffer
  412. * pointer.
  413. * \note Only works properly if ptr is an (unsigned char *).
  414. * \param ptr buffer
  415. * \param val 32-bit value
  416. */
  417. #define YASM_READ_32_B(val, ptr) \
  418. do { \
  419. (val) = (*((ptr)++) & 0xFF) << 24; \
  420. (val) |= (*((ptr)++) & 0xFF) << 16; \
  421. (val) |= (*((ptr)++) & 0xFF) << 8; \
  422. (val) |= *((ptr)++) & 0xFF; \
  423. } while (0)
  424. /** Read an 8-bit value from a buffer. Does not increment buffer pointer.
  425. * \note Only works properly if ptr is an (unsigned char *).
  426. * \param ptr buffer
  427. * \param val 8-bit value
  428. */
  429. #define YASM_LOAD_8(val, ptr) \
  430. (val) = *(ptr) & 0xFF
  431. /** Read a 16-bit value from a buffer in little endian. Does not increment
  432. * buffer pointer.
  433. * \note Only works properly if ptr is an (unsigned char *).
  434. * \param ptr buffer
  435. * \param val 16-bit value
  436. */
  437. #define YASM_LOAD_16_L(val, ptr) \
  438. do { \
  439. (val) = *(ptr) & 0xFF; \
  440. (val) |= (*((ptr)+1) & 0xFF) << 8; \
  441. } while (0)
  442. /** Read a 32-bit value from a buffer in little endian. Does not increment
  443. * buffer pointer.
  444. * \note Only works properly if ptr is an (unsigned char *).
  445. * \param ptr buffer
  446. * \param val 32-bit value
  447. */
  448. #define YASM_LOAD_32_L(val, ptr) \
  449. do { \
  450. (val) = (unsigned long)(*(ptr) & 0xFF); \
  451. (val) |= (unsigned long)((*((ptr)+1) & 0xFF) << 8); \
  452. (val) |= (unsigned long)((*((ptr)+2) & 0xFF) << 16); \
  453. (val) |= (unsigned long)((*((ptr)+3) & 0xFF) << 24); \
  454. } while (0)
  455. /** Read a 16-bit value from a buffer in big endian. Does not increment buffer
  456. * pointer.
  457. * \note Only works properly if ptr is an (unsigned char *).
  458. * \param ptr buffer
  459. * \param val 16-bit value
  460. */
  461. #define YASM_LOAD_16_B(val, ptr) \
  462. do { \
  463. (val) = (*(ptr) & 0xFF) << 8; \
  464. (val) |= *((ptr)+1) & 0xFF; \
  465. } while (0)
  466. /** Read a 32-bit value from a buffer in big endian. Does not increment buffer
  467. * pointer.
  468. * \note Only works properly if ptr is an (unsigned char *).
  469. * \param ptr buffer
  470. * \param val 32-bit value
  471. */
  472. #define YASM_LOAD_32_B(val, ptr) \
  473. do { \
  474. (val) = (unsigned long)((*(ptr) & 0xFF) << 24); \
  475. (val) |= (unsigned long)((*((ptr)+1) & 0xFF) << 16); \
  476. (val) |= (unsigned long)((*((ptr)+2) & 0xFF) << 8); \
  477. (val) |= (unsigned long)(*((ptr)+3) & 0xFF); \
  478. } while (0)
  479. #endif