SHARE
TWEET

Upcoming version of RGBDS-structs

ISSOtm Feb 3rd, 2019 113 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1.  
  2. ; MIT License
  3. ;
  4. ; Copyright (c) 2018 Eldred Habert
  5. ; Originally hosted at https://github.com/ISSOtm/rgbds-structs
  6. ;
  7. ; Permission is hereby granted, free of charge, to any person obtaining a copy
  8. ; of this software and associated documentation files (the "Software"), to deal
  9. ; in the Software without restriction, including without limitation the rights
  10. ; to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  11. ; copies of the Software, and to permit persons to whom the Software is
  12. ; furnished to do so, subject to the following conditions:
  13. ;
  14. ; The above copyright notice and this permission notice shall be included in all
  15. ; copies or substantial portions of the Software.
  16. ;
  17. ; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  18. ; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  19. ; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  20. ; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  21. ; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  22. ; OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  23. ; SOFTWARE.
  24.  
  25.  
  26. CORRECT_BEHAVIOR equ 1 ; Undefine this to disable SHIFT workaround
  27.  
  28.  
  29. ; struct struct_name
  30. ; Begins a struct declaration
  31. struct: MACRO
  32.     IF DEF(NB_FIELDS)
  33.         FAIL "Please close struct definitions using `end_struct`"
  34.     ENDC
  35.  
  36. STRUCT_NAME equs "\1"
  37.  
  38. NB_FIELDS = 0
  39.     RSRESET
  40. ENDM
  41.  
  42. ; end_struct
  43. ; Ends a struct declaration
  44. end_struct: MACRO
  45. ; Set nb of fields
  46. STRUCT_NB_FIELDS equs "{STRUCT_NAME}_nb_fields"
  47. STRUCT_NB_FIELDS = NB_FIELDS
  48.     PURGE STRUCT_NB_FIELDS
  49.  
  50. ; Set size of struct
  51. STRUCT_SIZEOF equs "sizeof_{STRUCT_NAME}"
  52. STRUCT_SIZEOF RB 0
  53.     PURGE STRUCT_SIZEOF
  54.  
  55.     PURGE NB_FIELDS
  56.     PURGE STRUCT_NAME
  57. ENDM
  58.  
  59.  
  60. ; field_name_from_id field_id
  61. ; For internal use, please do not use externally
  62. field_name_from_id: MACRO
  63. FIELD_ID_STR equs "{\1}"
  64. STRUCT_FIELD equs STRCAT("{STRUCT_NAME}_field", STRSUB("{FIELD_ID_STR}", 2, STRLEN("{FIELD_ID_STR}") - 1))
  65. STRUCT_FIELD_NAME equs "{STRUCT_FIELD}_name"
  66. STRUCT_FIELD_TYPE equs "{STRUCT_FIELD}_type"
  67. STRUCT_FIELD_NBEL equs "{STRUCT_FIELD}_nb_el" ; Number of elements
  68. STRUCT_FIELD_SIZE equs "{STRUCT_FIELD}_size" ; sizeof(type) * nb_el
  69. ENDM
  70.  
  71.  
  72. ; new_field nb_elems, rs_type, field_name
  73. ; For internal use, please do not use externally
  74. new_field: MACRO
  75.     IF !DEF(STRUCT_NAME) || !DEF(NB_FIELDS)
  76.         FAIL "Please start defining a struct, using `define_struct`"
  77.     ENDC
  78.  
  79.     field_name_from_id NB_FIELDS
  80. ; Set field name
  81. STRUCT_FIELD_NAME equs "\"\3\""
  82.     PURGE STRUCT_FIELD_NAME
  83.  
  84. ; Set field offset
  85. STRUCT_FIELD \2 (\1)
  86. ; Alias this in a human-comprehensive manner
  87. STRUCT_FIELD_NAME equs "{STRUCT_NAME}_\3"
  88. STRUCT_FIELD_NAME = STRUCT_FIELD
  89.  
  90. ; Calculate field size
  91. CURRENT_RS RB 0
  92. STRUCT_FIELD_SIZE = CURRENT_RS - STRUCT_FIELD
  93.  
  94. ; Set properties
  95. STRUCT_FIELD_NBEL = \1
  96. STRUCT_FIELD_TYPE equs STRSUB("\2", 2, 1)
  97.  
  98.     PURGE FIELD_ID_STR
  99.     PURGE STRUCT_FIELD
  100.     PURGE STRUCT_FIELD_NAME
  101.     PURGE STRUCT_FIELD_TYPE
  102.     PURGE STRUCT_FIELD_NBEL
  103.     PURGE STRUCT_FIELD_SIZE
  104.     PURGE CURRENT_RS
  105.  
  106. NB_FIELDS = NB_FIELDS + 1
  107. ENDM
  108.  
  109. ; bytes nb_bytes, field_name
  110. ; Defines a field of N bytes
  111. bytes: MACRO
  112.     new_field \1, RB, \2
  113. ENDM
  114.  
  115. ; words nb_words, field_name
  116. ; Defines a field of N*2 bytes
  117. words: MACRO
  118.     new_field \1, RW, \2
  119. ENDM
  120.  
  121. ; longs nb_longs, field_name
  122. ; Defines a field of N*4 bytes
  123. longs: MACRO
  124.     new_field \1, RL, \2
  125. ENDM
  126.  
  127.  
  128. ; dstruct struct_type, var_name[, ...]
  129. ; Allocates space for a struct in memory
  130. ; If no further arguments are supplied, the space is simply allocated (using `ds`)
  131. ; Otherwise, the data is written to memory using the appropriate types
  132. ; For example, a struct defined with `bytes 1, Field1` and `words 3, Field2` would have four extra arguments, one byte then three words.
  133. dstruct: MACRO
  134. NB_FIELDS equs "\1_nb_fields"
  135.     IF !DEF(NB_FIELDS)
  136.         FAIL "Struct \1 isn't defined!"
  137.     ENDC
  138. STRUCT_NAME equs "\1" ; Target this struct for `field_name_from_id`
  139. VAR_NAME    equs "\2"
  140.  
  141. VAR_NAME:: ; Declare the struct's root
  142.  
  143. FIELD_ID = 0
  144.     REPT NB_FIELDS
  145.  
  146.         field_name_from_id FIELD_ID
  147. FIELD_NAME equs STRCAT("{VAR_NAME}_", STRUCT_FIELD_NAME)
  148. FIELD_NAME::
  149.         IF _NARG == 2 ; RAM definition, no data
  150.             ds STRUCT_FIELD_SIZE
  151.         ELSE
  152. TMP equs STRCAT("\{", STRCAT("{STRUCT_FIELD_TYPE}", "\}")) ; Temp var for double deref because "{{STRUCT_FIELD_TYPE}}" is a syntax error
  153. DATA_TYPE equs STRCAT("D", TMP)
  154.             PURGE TMP
  155.             PRINTT "FIELD: {FIELD_NAME}\n"
  156. IF DEF(CORRECT_BEHAVIOR)
  157. SHIFT_FIELDS equs ""
  158. ENDC
  159.             REPT STRUCT_FIELD_NBEL
  160.                 DATA_TYPE \3
  161.                 PRINTT "{DATA_TYPE} \3\n"
  162.                 SHIFT
  163. IF DEF(CORRECT_BEHAVIOR)
  164. ; Hack because RGBDS saves the macro arguments when entering REPT blocks: I have to shift them outside as well
  165. TMP equs "{SHIFT_FIELDS}\n\tSHIFT"
  166.     PURGE SHIFT_FIELDS
  167. SHIFT_FIELDS equs "{TMP}"
  168.     PURGE TMP
  169. ENDC
  170.             ENDR
  171. IF DEF(CORRECT_BEHAVIOR)
  172.     SHIFT_FIELDS
  173.     PURGE SHIFT_FIELDS
  174. ENDC
  175.             PURGE DATA_TYPE
  176.         ENDC
  177.  
  178.         ; Clean up vars for next iteration
  179.         PURGE FIELD_ID_STR
  180.         PURGE STRUCT_FIELD
  181.         PURGE STRUCT_FIELD_NAME
  182.         PURGE STRUCT_FIELD_TYPE
  183.         PURGE STRUCT_FIELD_NBEL
  184.         PURGE STRUCT_FIELD_SIZE
  185.         PURGE FIELD_NAME
  186.  
  187. FIELD_ID = FIELD_ID + 1
  188.     ENDR
  189.  
  190.  
  191.     ; Define variable's properties from struct's
  192. \2_nb_fields = NB_FIELDS
  193. sizeof_\2 = sizeof_\1
  194.  
  195.  
  196.     ; Clean up
  197.     PURGE NB_FIELDS
  198.     PURGE STRUCT_NAME
  199.     PURGE VAR_NAME
  200.     PURGE FIELD_ID
  201. ENDM
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
Not a member of Pastebin yet?
Sign Up, it unlocks many cool features!
 
Top