integers.h 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154
  1. /* integers.h: Definitions for integers with arbitrary endianness
  2. Copyright (C) 2002-2003 Sebastian Reichelt
  3. This program is free software; you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation; either version 2, or (at your option)
  6. any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program; if not, write to the Free Software Foundation,
  13. Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
  14. #ifndef INTEGERS_H
  15. #define INTEGERS_H
  16. #include "generic.h"
  17. #define TARGET_BIG_ENDIAN
  18. // *** Zero Integer Definitions ***
  19. typedef I1 ZI1;
  20. typedef I2 ZI2;
  21. typedef I4 ZI4;
  22. #define IsZero(I) (!(I))
  23. #ifdef __i386__
  24. // This only works on targets which don't care about alignment.
  25. #define IsZeroI1(I) (IsZero (*((ZI1 *) &(I))))
  26. #define IsZeroI2(I) (IsZero (*((ZI2 *) &(I))))
  27. #define IsZeroI4(I) (IsZero (*((ZI4 *) &(I))))
  28. #else
  29. // Use only bytewise reads for targets which do care about alignment.
  30. #define IsZeroI1(I) (IsZero (ReadTI1 (*(TI1*)&(I))))
  31. #define IsZeroI2(I) (IsZero (ReadTI2 (*(TI2*)&(I))))
  32. #define IsZeroI4(I) (IsZero (ReadTI4 (*(TI4*)&(I))))
  33. #endif
  34. // *** Target Integer Definitions ***
  35. // 1 Byte Target Integer
  36. // Defined as structure to avoid unguarded reading/writing.
  37. typedef struct ATTRIBUTE_PACKED {
  38. I1 Val;
  39. } TI1;
  40. // 2 Byte Target Integer
  41. typedef struct ATTRIBUTE_PACKED {
  42. #ifdef TARGET_BIG_ENDIAN
  43. TI1 Hi, Lo;
  44. #else /* !TARGET_BIG_ENDIAN */
  45. TI1 Lo, Hi;
  46. #endif /* !TARGET_BIG_ENDIAN */
  47. } TI2;
  48. // 4 Byte Target Integer
  49. typedef struct ATTRIBUTE_PACKED {
  50. #ifdef TARGET_BIG_ENDIAN
  51. TI2 Hi, Lo;
  52. #else /* !TARGET_BIG_ENDIAN */
  53. TI2 Lo, Hi;
  54. #endif /* !TARGET_BIG_ENDIAN */
  55. } TI4;
  56. // *** Host Integer Definitions ***
  57. // 1 Byte Host Integer
  58. // Defined as structure to avoid unguarded reading/writing.
  59. typedef struct ATTRIBUTE_PACKED {
  60. unsigned char Val;
  61. } HI1;
  62. // 2 Byte Host Integer
  63. typedef struct ATTRIBUTE_PACKED {
  64. #ifdef HOST_BIG_ENDIAN
  65. HI1 Hi, Lo;
  66. #else /* !HOST_BIG_ENDIAN */
  67. HI1 Lo, Hi;
  68. #endif /* !HOST_BIG_ENDIAN */
  69. } HI2;
  70. // 4 Byte Host Integer
  71. typedef struct ATTRIBUTE_PACKED {
  72. #ifdef HOST_BIG_ENDIAN
  73. HI2 Hi, Lo;
  74. #else /* !HOST_BIG_ENDIAN */
  75. HI2 Lo, Hi;
  76. #endif /* !HOST_BIG_ENDIAN */
  77. } HI4;
  78. // *** Macros to read arbitrary integers ***
  79. #define ReadI1(I) ((I).Val)
  80. #define ReadI2(I) ((ReadI1 ((I).Hi) << 8) | ReadI1 ((I).Lo))
  81. #define ReadI4(I) ((ReadI2 ((I).Hi) << 16) | ReadI2 ((I).Lo))
  82. // *** Functions to read integers ***
  83. #define DEFINE_INT_SIZE(size) I##size ReadTI##size (const TI##size I); I##size ReadHI##size (const HI##size I);
  84. #include "int_def.inc"
  85. #undef DEFINE_INT_SIZE
  86. // *** Macros to write arbitrary integers ***
  87. #define WriteI1(I,V) ((I).Val = (V))
  88. #define WriteI2(I,V) ({ register I2 __V2 = (V); WriteI1 ((I).Hi, (__V2) >> 8); WriteI1 ((I).Lo, (__V2)); })
  89. #define WriteI4(I,V) ({ register I4 __V4 = (V); WriteI2 ((I).Hi, (__V4) >> 16); WriteI2 ((I).Lo, (__V4)); })
  90. // *** Functions to write integers ***
  91. #define DEFINE_INT_SIZE(size) void WriteTI##size##_ (TI##size *I, I##size V); void WriteHI##size##_ (HI##size *I, I##size V);
  92. #include "int_def.inc"
  93. #undef DEFINE_INT_SIZE
  94. #define WriteTI1(I,V) (WriteTI1_ (&(I), (V)))
  95. #define WriteTI2(I,V) (WriteTI2_ (&(I), (V)))
  96. #define WriteTI4(I,V) (WriteTI4_ (&(I), (V)))
  97. #define WriteHI1(I,V) (WriteHI1_ (&(I), (V)))
  98. #define WriteHI2(I,V) (WriteHI2_ (&(I), (V)))
  99. #define WriteHI4(I,V) (WriteHI4_ (&(I), (V)))
  100. // *** Functions to read arbitrary-length target integers ***
  101. // Read an unsigned target integer of specified size from a
  102. // data buffer.
  103. IMAX ReadTI (const void *Data, SIZE Size);
  104. // Read a signed target integer of specified size from a
  105. // data buffer.
  106. SIMAX ReadSTI (const void *Data, SIZE Size);
  107. // *** Functions to write arbitrary-length target integers ***
  108. // Write a target integer of specified size to a data buffer.
  109. // The integer may be interpreted as a signed or unsigned
  110. // value based on the AllowSigned and AllowUnsigned parameters.
  111. // If the value does not fit into the contents, FALSE is
  112. // returned.
  113. BOOLEAN WriteTI (void *Data, SIZE Size, SIMAX Value, BOOLEAN AllowSigned, BOOLEAN AllowUnsigned);
  114. // Add a target integer of specified size to a data buffer.
  115. // The integer may be interpreted as a signed or unsigned
  116. // value based on the AllowSigned and AllowUnsigned parameters.
  117. // If the value does not fit into the contents, FALSE is
  118. // returned.
  119. BOOLEAN AddTI (void *Data, SIZE Size, SIMAX Value, BOOLEAN AllowSigned, BOOLEAN AllowUnsigned);
  120. #endif