asmasm.asm 53 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118
  1. ;; This file is part of asmc, a bootstrapping OS with minimal seed
  2. ;; Copyright (C) 2018 Giovanni Mascellani <gio@debian.org>
  3. ;; https://gitlab.com/giomasce/asmc
  4. ;; This program is free software: you can redistribute it and/or modify
  5. ;; it under the terms of the GNU General Public License as published by
  6. ;; the Free Software Foundation, either version 3 of the License, or
  7. ;; (at your option) any later version.
  8. ;; This program is distributed in the hope that it will be useful,
  9. ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11. ;; GNU General Public License for more details.
  12. ;; You should have received a copy of the GNU General Public License
  13. ;; along with this program. If not, see <https://www.gnu.org/licenses/>.
  14. OP_PUSH equ 0
  15. OP_POP equ 1
  16. OP_ADD equ 2
  17. OP_SUB equ 3
  18. OP_MOV equ 4
  19. OP_CMP equ 5
  20. OP_AND equ 6
  21. OP_OR equ 7
  22. OP_JMP equ 8
  23. OP_CALL equ 9
  24. OP_JE equ 10
  25. OP_JNE equ 11
  26. OP_JA equ 12
  27. OP_JNA equ 13
  28. OP_JAE equ 14
  29. OP_JNAE equ 15
  30. OP_JB equ 16
  31. OP_JNB equ 17
  32. OP_JBE equ 18
  33. OP_JNBE equ 19
  34. OP_JG equ 20
  35. OP_JNG equ 21
  36. OP_JGE equ 22
  37. OP_JNGE equ 23
  38. OP_JL equ 24
  39. OP_JNL equ 25
  40. OP_JLE equ 26
  41. OP_JNLE equ 27
  42. OP_MUL equ 28
  43. OP_IMUL equ 29
  44. OP_INT equ 30
  45. OP_RET equ 31
  46. OP_IN equ 32
  47. OP_OUT equ 33
  48. OP_DIV equ 34
  49. OP_IDIV equ 35
  50. OP_NEG equ 36
  51. OP_NOT equ 37
  52. OP_XOR equ 38
  53. OP_TEST equ 39
  54. OP_HLT equ 40
  55. OP_RDPMC equ 41
  56. OP_RDMSR equ 42
  57. OP_WRMSR equ 43
  58. OP_CPUID equ 44
  59. OP_SHL equ 45
  60. OP_SHR equ 46
  61. OP_SAL equ 47
  62. OP_SAR equ 48
  63. section .data
  64. opcode_names:
  65. db 'push'
  66. db 0
  67. db 'pop'
  68. db 0
  69. db 'add'
  70. db 0
  71. db 'sub'
  72. db 0
  73. db 'mov'
  74. db 0
  75. db 'cmp'
  76. db 0
  77. db 'and'
  78. db 0
  79. db 'or'
  80. db 0
  81. db 'jmp'
  82. db 0
  83. db 'call'
  84. db 0
  85. db 'je'
  86. db 0
  87. db 'jne'
  88. db 0
  89. db 'ja'
  90. db 0
  91. db 'jna'
  92. db 0
  93. db 'jae'
  94. db 0
  95. db 'jnae'
  96. db 0
  97. db 'jb'
  98. db 0
  99. db 'jnb'
  100. db 0
  101. db 'jbe'
  102. db 0
  103. db 'jnbe'
  104. db 0
  105. db 'jg'
  106. db 0
  107. db 'jng'
  108. db 0
  109. db 'jge'
  110. db 0
  111. db 'jnge'
  112. db 0
  113. db 'jl'
  114. db 0
  115. db 'jnl'
  116. db 0
  117. db 'jle'
  118. db 0
  119. db 'jnle'
  120. db 0
  121. db 'mul'
  122. db 0
  123. db 'imul'
  124. db 0
  125. db 'int'
  126. db 0
  127. db 'ret'
  128. db 0
  129. db 'in'
  130. db 0
  131. db 'out'
  132. db 0
  133. db 'div'
  134. db 0
  135. db 'idiv'
  136. db 0
  137. db 'neg'
  138. db 0
  139. db 'not'
  140. db 0
  141. db 'xor'
  142. db 0
  143. db 'test'
  144. db 0
  145. db 'hlt'
  146. db 0
  147. db 'rdpmc'
  148. db 0
  149. db 'rdmsr'
  150. db 0
  151. db 'wrmsr'
  152. db 0
  153. db 'cpuid'
  154. db 0
  155. db 'shl'
  156. db 0
  157. db 'shr'
  158. db 0
  159. db 'sal'
  160. db 0
  161. db 'sar'
  162. db 0
  163. db 0
  164. opcode_funcs:
  165. dd process_push_like ; OP_PUSH
  166. dd process_push_like ; OP_POP
  167. dd process_add_like ; OP_ADD
  168. dd process_add_like ; OP_SUB
  169. dd process_add_like ; OP_MOV
  170. dd process_add_like ; OP_CMP
  171. dd process_add_like ; OP_AND
  172. dd process_add_like ; OP_OR
  173. dd process_jmp_like ; OP_JMP
  174. dd process_jmp_like ; OP_CALL
  175. dd process_jmp_like ; OP_JE
  176. dd process_jmp_like ; OP_JNE
  177. dd process_jmp_like ; OP_JA
  178. dd process_jmp_like ; OP_JNA
  179. dd process_jmp_like ; OP_JAE
  180. dd process_jmp_like ; OP_JNAE
  181. dd process_jmp_like ; OP_JB
  182. dd process_jmp_like ; OP_JNB
  183. dd process_jmp_like ; OP_JBE
  184. dd process_jmp_like ; OP_JNBE
  185. dd process_jmp_like ; OP_JG
  186. dd process_jmp_like ; OP_JNG
  187. dd process_jmp_like ; OP_JGE
  188. dd process_jmp_like ; OP_JNGE
  189. dd process_jmp_like ; OP_JL
  190. dd process_jmp_like ; OP_JNL
  191. dd process_jmp_like ; OP_JLE
  192. dd process_jmp_like ; OP_JNLE
  193. dd process_jmp_like ; OP_MUL
  194. dd process_jmp_like ; OP_IMUL
  195. dd process_int ; OP_INT
  196. dd process_ret_like ; OP_RET
  197. dd process_in_like ; OP_IN
  198. dd process_in_like ; OP_OUT
  199. dd process_jmp_like ; OP_DIV
  200. dd process_jmp_like ; OP_IDIV
  201. dd process_jmp_like ; OP_NEG
  202. dd process_jmp_like ; OP_NOT
  203. dd process_add_like ; OP_XOR
  204. dd process_add_like ; OP_TEST
  205. dd process_hlt ; OP_HLT
  206. dd process_ret_like ; OP_RDPMC
  207. dd process_ret_like ; OP_RDMSR
  208. dd process_ret_like ; OP_WRMSR
  209. dd process_ret_like ; OP_CPUID
  210. dd process_push_like ; OP_SHL
  211. dd process_push_like ; OP_SHR
  212. dd process_push_like ; OP_SAL
  213. dd process_push_like ; OP_SAR
  214. empty_opcode:
  215. dd 0xf0 ; OP_PUSH
  216. dd 0xf0 ; OP_POP
  217. dd 0xf0 ; OP_ADD
  218. dd 0xf0 ; OP_SUB
  219. dd 0xf0 ; OP_MOV
  220. dd 0xf0 ; OP_CMP
  221. dd 0xf0 ; OP_AND
  222. dd 0xf0 ; OP_OR
  223. dd 0xf0 ; OP_JMP
  224. dd 0xf0 ; OP_CALL
  225. dd 0xf0 ; OP_JE
  226. dd 0xf0 ; OP_JNE
  227. dd 0xf0 ; OP_JA
  228. dd 0xf0 ; OP_JNA
  229. dd 0xf0 ; OP_JAE
  230. dd 0xf0 ; OP_JNAE
  231. dd 0xf0 ; OP_JB
  232. dd 0xf0 ; OP_JNB
  233. dd 0xf0 ; OP_JBE
  234. dd 0xf0 ; OP_JNBE
  235. dd 0xf0 ; OP_JG
  236. dd 0xf0 ; OP_JNG
  237. dd 0xf0 ; OP_JGE
  238. dd 0xf0 ; OP_JNGE
  239. dd 0xf0 ; OP_JL
  240. dd 0xf0 ; OP_JNL
  241. dd 0xf0 ; OP_JLE
  242. dd 0xf0 ; OP_JNLE
  243. dd 0xf0 ; OP_MUL
  244. dd 0xf0 ; OP_IMUL
  245. dd 0xf0 ; OP_INT
  246. dd 0xc3 ; OP_RET
  247. dd 0xf0 ; OP_IN
  248. dd 0xf0 ; OP_OUT
  249. dd 0xf0 ; OP_DIV
  250. dd 0xf0 ; OP_IDIV
  251. dd 0xf0 ; OP_NEG
  252. dd 0xf0 ; OP_NOT
  253. dd 0xf0 ; OP_XOR
  254. dd 0xf0 ; OP_TEST
  255. dd 0xf0 ; OP_HLT
  256. dd 0x1330f ; OP_RDPMC
  257. dd 0x1320f ; OP_RDMSR
  258. dd 0x1300f ; OP_WRMSR
  259. dd 0x1a20f ; OP_CPUID
  260. dd 0xf0 ; OP_SHL
  261. dd 0xf0 ; OP_SHR
  262. dd 0xf0 ; OP_SAL
  263. dd 0xf0 ; OP_SAR
  264. rm32_opcode:
  265. dd 0x06ff ; OP_PUSH
  266. dd 0x008f ; OP_POP
  267. dd 0xf0 ; OP_ADD
  268. dd 0xf0 ; OP_SUB
  269. dd 0xf0 ; OP_MOV
  270. dd 0xf0 ; OP_CMP
  271. dd 0xf0 ; OP_AND
  272. dd 0xf0 ; OP_OR
  273. dd 0x04ff ; OP_JMP
  274. dd 0x02ff ; OP_CALL
  275. dd 0xf0 ; OP_JE
  276. dd 0xf0 ; OP_JNE
  277. dd 0xf0 ; OP_JA
  278. dd 0xf0 ; OP_JNA
  279. dd 0xf0 ; OP_JAE
  280. dd 0xf0 ; OP_JNAE
  281. dd 0xf0 ; OP_JB
  282. dd 0xf0 ; OP_JNB
  283. dd 0xf0 ; OP_JBE
  284. dd 0xf0 ; OP_JNBE
  285. dd 0xf0 ; OP_JG
  286. dd 0xf0 ; OP_JNG
  287. dd 0xf0 ; OP_JGE
  288. dd 0xf0 ; OP_JNGE
  289. dd 0xf0 ; OP_JL
  290. dd 0xf0 ; OP_JNL
  291. dd 0xf0 ; OP_JLE
  292. dd 0xf0 ; OP_JNLE
  293. dd 0x04f7 ; OP_MUL
  294. dd 0x05f7 ; OP_IMUL
  295. dd 0xf0 ; OP_INT
  296. dd 0xf0 ; OP_RET
  297. dd 0xf0 ; OP_IN
  298. dd 0xf0 ; OP_OUT
  299. dd 0x06f7 ; OP_DIV
  300. dd 0x07f7 ; OP_IDIV
  301. dd 0x03f7 ; OP_NEG
  302. dd 0x02f7 ; OP_NOT
  303. dd 0xf0 ; OP_XOR
  304. dd 0xf0 ; OP_TEST
  305. dd 0xf0 ; OP_HLT
  306. dd 0xf0 ; OP_RDPMC
  307. dd 0xf0 ; OP_RDMSR
  308. dd 0xf0 ; OP_WRMSR
  309. dd 0xf0 ; OP_CPUID
  310. dd 0x04d3 ; OP_SHL
  311. dd 0x05d3 ; OP_SHR
  312. dd 0x04d3 ; OP_SAL
  313. dd 0x07d3 ; OP_SAR
  314. imm32_opcode:
  315. dd 0xf0 ; OP_PUSH
  316. dd 0xf0 ; OP_POP
  317. dd 0xf0 ; OP_ADD
  318. dd 0xf0 ; OP_SUB
  319. dd 0xf0 ; OP_MOV
  320. dd 0xf0 ; OP_CMP
  321. dd 0xf0 ; OP_AND
  322. dd 0xf0 ; OP_OR
  323. dd 0xe9 ; OP_JMP
  324. dd 0xe8 ; OP_CALL
  325. dd 0x1840f ; OP_JE
  326. dd 0x1850f ; OP_JNE
  327. dd 0x1870f ; OP_JA
  328. dd 0x1860f ; OP_JNA
  329. dd 0x1830f ; OP_JAE
  330. dd 0x1820f ; OP_JNAE
  331. dd 0x1820f ; OP_JB
  332. dd 0x1830f ; OP_JNB
  333. dd 0x1860f ; OP_JBE
  334. dd 0x1870f ; OP_JNBE
  335. dd 0x18f0f ; OP_JG
  336. dd 0x18e0f ; OP_JNG
  337. dd 0x18d0f ; OP_JGE
  338. dd 0x18c0f ; OP_JNGE
  339. dd 0x18c0f ; OP_JL
  340. dd 0x18d0f ; OP_JNL
  341. dd 0x18e0f ; OP_JLE
  342. dd 0x18f0f ; OP_JNLE
  343. dd 0xf0 ; OP_MUL
  344. dd 0xf0 ; OP_IMUL
  345. dd 0xf0 ; OP_INT
  346. dd 0xf0 ; OP_RET
  347. dd 0xf0 ; OP_IN
  348. dd 0xf0 ; OP_OUT
  349. dd 0xf0 ; OP_DIV
  350. dd 0xf0 ; OP_IDIV
  351. dd 0xf0 ; OP_NEG
  352. dd 0xf0 ; OP_NOT
  353. dd 0xf0 ; OP_XOR
  354. dd 0xf0 ; OP_TEST
  355. dd 0xf0 ; OP_HLT
  356. dd 0xf0 ; OP_RDPMC
  357. dd 0xf0 ; OP_RDMSR
  358. dd 0xf0 ; OP_WRMSR
  359. dd 0xf0 ; OP_CPUID
  360. dd 0xf0 ; OP_SHL
  361. dd 0xf0 ; OP_SHR
  362. dd 0xf0 ; OP_SAL
  363. dd 0xf0 ; OP_SAR
  364. r8rm8_opcode:
  365. dd 0xf0 ; OP_PUSH
  366. dd 0xf0 ; OP_POP
  367. dd 0x02 ; OP_ADD
  368. dd 0x2a ; OP_SUB
  369. dd 0x8a ; OP_MOV
  370. dd 0x3a ; OP_CMP
  371. dd 0x22 ; OP_AND
  372. dd 0x0a ; OP_OR
  373. dd 0xf0 ; OP_JMP
  374. dd 0xf0 ; OP_CALL
  375. dd 0xf0 ; OP_JE
  376. dd 0xf0 ; OP_JNE
  377. dd 0xf0 ; OP_JA
  378. dd 0xf0 ; OP_JNA
  379. dd 0xf0 ; OP_JAE
  380. dd 0xf0 ; OP_JNAE
  381. dd 0xf0 ; OP_JB
  382. dd 0xf0 ; OP_JNB
  383. dd 0xf0 ; OP_JBE
  384. dd 0xf0 ; OP_JNBE
  385. dd 0xf0 ; OP_JG
  386. dd 0xf0 ; OP_JNG
  387. dd 0xf0 ; OP_JGE
  388. dd 0xf0 ; OP_JNGE
  389. dd 0xf0 ; OP_JL
  390. dd 0xf0 ; OP_JNL
  391. dd 0xf0 ; OP_JLE
  392. dd 0xf0 ; OP_JNLE
  393. dd 0xf0 ; OP_MUL
  394. dd 0xf0 ; OP_IMUL
  395. dd 0xf0 ; OP_INT
  396. dd 0xf0 ; OP_RET
  397. dd 0xf0 ; OP_IN
  398. dd 0xf0 ; OP_OUT
  399. dd 0xf0 ; OP_DIV
  400. dd 0xf0 ; OP_IDIV
  401. dd 0xf0 ; OP_NEG
  402. dd 0xf0 ; OP_NOT
  403. dd 0x32 ; OP_XOR
  404. dd 0x84 ; OP_TEST
  405. dd 0xf0 ; OP_HLT
  406. dd 0xf0 ; OP_RDPMC
  407. dd 0xf0 ; OP_RDMSR
  408. dd 0xf0 ; OP_WRMSR
  409. dd 0xf0 ; OP_CPUID
  410. dd 0xf0 ; OP_SHL
  411. dd 0xf0 ; OP_SHR
  412. dd 0xf0 ; OP_SAL
  413. dd 0xf0 ; OP_SAR
  414. r32rm32_opcode:
  415. dd 0xf0 ; OP_PUSH
  416. dd 0xf0 ; OP_POP
  417. dd 0x03 ; OP_ADD
  418. dd 0x2b ; OP_SUB
  419. dd 0x8b ; OP_MOV
  420. dd 0x3b ; OP_CMP
  421. dd 0x23 ; OP_AND
  422. dd 0x0b ; OP_OR
  423. dd 0xf0 ; OP_JMP
  424. dd 0xf0 ; OP_CALL
  425. dd 0xf0 ; OP_JE
  426. dd 0xf0 ; OP_JNE
  427. dd 0xf0 ; OP_JA
  428. dd 0xf0 ; OP_JNA
  429. dd 0xf0 ; OP_JAE
  430. dd 0xf0 ; OP_JNAE
  431. dd 0xf0 ; OP_JB
  432. dd 0xf0 ; OP_JNB
  433. dd 0xf0 ; OP_JBE
  434. dd 0xf0 ; OP_JNBE
  435. dd 0xf0 ; OP_JG
  436. dd 0xf0 ; OP_JNG
  437. dd 0xf0 ; OP_JGE
  438. dd 0xf0 ; OP_JNGE
  439. dd 0xf0 ; OP_JL
  440. dd 0xf0 ; OP_JNL
  441. dd 0xf0 ; OP_JLE
  442. dd 0xf0 ; OP_JNLE
  443. dd 0xf0 ; OP_MUL
  444. dd 0xf0 ; OP_IMUL
  445. dd 0xf0 ; OP_INT
  446. dd 0xf0 ; OP_RET
  447. dd 0xf0 ; OP_IN
  448. dd 0xf0 ; OP_OUT
  449. dd 0xf0 ; OP_DIV
  450. dd 0xf0 ; OP_IDIV
  451. dd 0xf0 ; OP_NEG
  452. dd 0xf0 ; OP_NOT
  453. dd 0x33 ; OP_XOR
  454. dd 0x85 ; OP_TEST
  455. dd 0xf0 ; OP_HLT
  456. dd 0xf0 ; OP_RDPMC
  457. dd 0xf0 ; OP_RDMSR
  458. dd 0xf0 ; OP_WRMSR
  459. dd 0xf0 ; OP_CPUID
  460. dd 0xf0 ; OP_SHL
  461. dd 0xf0 ; OP_SHR
  462. dd 0xf0 ; OP_SAL
  463. dd 0xf0 ; OP_SAR
  464. rm8r8_opcode:
  465. dd 0xf0 ; OP_PUSH
  466. dd 0xf0 ; OP_POP
  467. dd 0x00 ; OP_ADD
  468. dd 0x28 ; OP_SUB
  469. dd 0x88 ; OP_MOV
  470. dd 0x38 ; OP_CMP
  471. dd 0x20 ; OP_AND
  472. dd 0x08 ; OP_OR
  473. dd 0xf0 ; OP_JMP
  474. dd 0xf0 ; OP_CALL
  475. dd 0xf0 ; OP_JE
  476. dd 0xf0 ; OP_JNE
  477. dd 0xf0 ; OP_JA
  478. dd 0xf0 ; OP_JNA
  479. dd 0xf0 ; OP_JAE
  480. dd 0xf0 ; OP_JNAE
  481. dd 0xf0 ; OP_JB
  482. dd 0xf0 ; OP_JNB
  483. dd 0xf0 ; OP_JBE
  484. dd 0xf0 ; OP_JNBE
  485. dd 0xf0 ; OP_JG
  486. dd 0xf0 ; OP_JNG
  487. dd 0xf0 ; OP_JGE
  488. dd 0xf0 ; OP_JNGE
  489. dd 0xf0 ; OP_JL
  490. dd 0xf0 ; OP_JNL
  491. dd 0xf0 ; OP_JLE
  492. dd 0xf0 ; OP_JNLE
  493. dd 0xf0 ; OP_MUL
  494. dd 0xf0 ; OP_IMUL
  495. dd 0xf0 ; OP_INT
  496. dd 0xf0 ; OP_RET
  497. dd 0xf0 ; OP_IN
  498. dd 0xf0 ; OP_OUT
  499. dd 0xf0 ; OP_DIV
  500. dd 0xf0 ; OP_IDIV
  501. dd 0xf0 ; OP_NEG
  502. dd 0xf0 ; OP_NOT
  503. dd 0x30 ; OP_XOR
  504. dd 0x84 ; OP_TEST
  505. dd 0xf0 ; OP_HLT
  506. dd 0xf0 ; OP_RDPMC
  507. dd 0xf0 ; OP_RDMSR
  508. dd 0xf0 ; OP_WRMSR
  509. dd 0xf0 ; OP_CPUID
  510. dd 0xf0 ; OP_SHL
  511. dd 0xf0 ; OP_SHR
  512. dd 0xf0 ; OP_SAL
  513. dd 0xf0 ; OP_SAR
  514. rm32r32_opcode:
  515. dd 0xf0 ; OP_PUSH
  516. dd 0xf0 ; OP_POP
  517. dd 0x01 ; OP_ADD
  518. dd 0x29 ; OP_SUB
  519. dd 0x89 ; OP_MOV
  520. dd 0x39 ; OP_CMP
  521. dd 0x21 ; OP_AND
  522. dd 0x09 ; OP_OR
  523. dd 0xf0 ; OP_JMP
  524. dd 0xf0 ; OP_CALL
  525. dd 0xf0 ; OP_JE
  526. dd 0xf0 ; OP_JNE
  527. dd 0xf0 ; OP_JA
  528. dd 0xf0 ; OP_JNA
  529. dd 0xf0 ; OP_JAE
  530. dd 0xf0 ; OP_JNAE
  531. dd 0xf0 ; OP_JB
  532. dd 0xf0 ; OP_JNB
  533. dd 0xf0 ; OP_JBE
  534. dd 0xf0 ; OP_JNBE
  535. dd 0xf0 ; OP_JG
  536. dd 0xf0 ; OP_JNG
  537. dd 0xf0 ; OP_JGE
  538. dd 0xf0 ; OP_JNGE
  539. dd 0xf0 ; OP_JL
  540. dd 0xf0 ; OP_JNL
  541. dd 0xf0 ; OP_JLE
  542. dd 0xf0 ; OP_JNLE
  543. dd 0xf0 ; OP_MUL
  544. dd 0xf0 ; OP_IMUL
  545. dd 0xf0 ; OP_INT
  546. dd 0xf0 ; OP_RET
  547. dd 0xf0 ; OP_IN
  548. dd 0xf0 ; OP_OUT
  549. dd 0xf0 ; OP_DIV
  550. dd 0xf0 ; OP_IDIV
  551. dd 0xf0 ; OP_NEG
  552. dd 0xf0 ; OP_NOT
  553. dd 0x31 ; OP_XOR
  554. dd 0x85 ; OP_TEST
  555. dd 0xf0 ; OP_HLT
  556. dd 0xf0 ; OP_RDPMC
  557. dd 0xf0 ; OP_RDMSR
  558. dd 0xf0 ; OP_WRMSR
  559. dd 0xf0 ; OP_CPUID
  560. dd 0xf0 ; OP_SHL
  561. dd 0xf0 ; OP_SHR
  562. dd 0xf0 ; OP_SAL
  563. dd 0xf0 ; OP_SAR
  564. rm8imm8_opcode:
  565. dd 0xf0 ; OP_PUSH
  566. dd 0xf0 ; OP_POP
  567. dd 0x0080 ; OP_ADD
  568. dd 0x0580 ; OP_SUB
  569. dd 0x00c6 ; OP_MOV
  570. dd 0x0780 ; OP_CMP
  571. dd 0x0480 ; OP_AND
  572. dd 0x0180 ; OP_OR
  573. dd 0xf0 ; OP_JMP
  574. dd 0xf0 ; OP_CALL
  575. dd 0xf0 ; OP_JE
  576. dd 0xf0 ; OP_JNE
  577. dd 0xf0 ; OP_JA
  578. dd 0xf0 ; OP_JNA
  579. dd 0xf0 ; OP_JAE
  580. dd 0xf0 ; OP_JNAE
  581. dd 0xf0 ; OP_JB
  582. dd 0xf0 ; OP_JNB
  583. dd 0xf0 ; OP_JBE
  584. dd 0xf0 ; OP_JNBE
  585. dd 0xf0 ; OP_JG
  586. dd 0xf0 ; OP_JNG
  587. dd 0xf0 ; OP_JGE
  588. dd 0xf0 ; OP_JNGE
  589. dd 0xf0 ; OP_JL
  590. dd 0xf0 ; OP_JNL
  591. dd 0xf0 ; OP_JLE
  592. dd 0xf0 ; OP_JNLE
  593. dd 0xf0 ; OP_MUL
  594. dd 0xf0 ; OP_IMUL
  595. dd 0xf0 ; OP_INT
  596. dd 0xf0 ; OP_RET
  597. dd 0xf0 ; OP_IN
  598. dd 0xf0 ; OP_OUT
  599. dd 0xf0 ; OP_DIV
  600. dd 0xf0 ; OP_IDIV
  601. dd 0xf0 ; OP_NEG
  602. dd 0xf0 ; OP_NOT
  603. dd 0x0680 ; OP_XOR
  604. dd 0x00f6 ; OP_TEST
  605. dd 0xf0 ; OP_HLT
  606. dd 0xf0 ; OP_RDPMC
  607. dd 0xf0 ; OP_RDMSR
  608. dd 0xf0 ; OP_WRMSR
  609. dd 0xf0 ; OP_CPUID
  610. dd 0xf0 ; OP_SHL
  611. dd 0xf0 ; OP_SHR
  612. dd 0xf0 ; OP_SAL
  613. dd 0xf0 ; OP_SAR
  614. rm32imm32_opcode:
  615. dd 0xf0 ; OP_PUSH
  616. dd 0xf0 ; OP_POP
  617. dd 0x0081 ; OP_ADD
  618. dd 0x0581 ; OP_SUB
  619. dd 0x00c7 ; OP_MOV
  620. dd 0x0781 ; OP_CMP
  621. dd 0x0481 ; OP_AND
  622. dd 0x0181 ; OP_OR
  623. dd 0xf0 ; OP_JMP
  624. dd 0xf0 ; OP_CALL
  625. dd 0xf0 ; OP_JE
  626. dd 0xf0 ; OP_JNE
  627. dd 0xf0 ; OP_JA
  628. dd 0xf0 ; OP_JNA
  629. dd 0xf0 ; OP_JAE
  630. dd 0xf0 ; OP_JNAE
  631. dd 0xf0 ; OP_JB
  632. dd 0xf0 ; OP_JNB
  633. dd 0xf0 ; OP_JBE
  634. dd 0xf0 ; OP_JNBE
  635. dd 0xf0 ; OP_JG
  636. dd 0xf0 ; OP_JNG
  637. dd 0xf0 ; OP_JGE
  638. dd 0xf0 ; OP_JNGE
  639. dd 0xf0 ; OP_JL
  640. dd 0xf0 ; OP_JNL
  641. dd 0xf0 ; OP_JLE
  642. dd 0xf0 ; OP_JNLE
  643. dd 0xf0 ; OP_MUL
  644. dd 0xf0 ; OP_IMUL
  645. dd 0xf0 ; OP_INT
  646. dd 0xf0 ; OP_RET
  647. dd 0xf0 ; OP_IN
  648. dd 0xf0 ; OP_OUT
  649. dd 0xf0 ; OP_DIV
  650. dd 0xf0 ; OP_IDIV
  651. dd 0xf0 ; OP_NEG
  652. dd 0xf0 ; OP_NOT
  653. dd 0x0681 ; OP_XOR
  654. dd 0x00f7 ; OP_TEST
  655. dd 0xf0 ; OP_HLT
  656. dd 0xf0 ; OP_RDPMC
  657. dd 0xf0 ; OP_RDMSR
  658. dd 0xf0 ; OP_WRMSR
  659. dd 0xf0 ; OP_CPUID
  660. dd 0xf0 ; OP_SHL
  661. dd 0xf0 ; OP_SHR
  662. dd 0xf0 ; OP_SAL
  663. dd 0xf0 ; OP_SAR
  664. reg_eax:
  665. db 'eax'
  666. db 0
  667. reg_ecx:
  668. db 'ecx'
  669. db 0
  670. reg_edx:
  671. db 'edx'
  672. db 0
  673. reg_ebx:
  674. db 'ebx'
  675. db 0
  676. reg_esp:
  677. db 'esp'
  678. db 0
  679. reg_ebp:
  680. db 'ebp'
  681. db 0
  682. reg_esi:
  683. db 'esi'
  684. db 0
  685. reg_edi:
  686. db 'edi'
  687. db 0
  688. reg_al:
  689. db 'al'
  690. db 0
  691. reg_cl:
  692. db 'cl'
  693. db 0
  694. reg_dl:
  695. db 'dl'
  696. db 0
  697. reg_bl:
  698. db 'bl'
  699. db 0
  700. reg_ah:
  701. db 'ah'
  702. db 0
  703. reg_ch:
  704. db 'ch'
  705. db 0
  706. reg_dh:
  707. db 'dh'
  708. db 0
  709. reg_bh:
  710. db 'bh'
  711. db 0
  712. reg_ax:
  713. db 'ax'
  714. db 0
  715. reg_dx:
  716. db 'dx'
  717. db 0
  718. str_BYTE:
  719. db 'BYTE'
  720. db 0
  721. str_DWORD:
  722. db 'DWORD'
  723. db 0
  724. str_resb:
  725. db 'resb'
  726. db 0
  727. str_resd:
  728. db 'resd'
  729. db 0
  730. str_dd:
  731. db 'dd'
  732. db 0
  733. str_db:
  734. db 'db'
  735. db 0
  736. str_section:
  737. db 'section'
  738. db 0
  739. str_org:
  740. db 'org'
  741. db 0
  742. str_bits:
  743. db 'bits'
  744. db 0
  745. str_global:
  746. db 'global'
  747. db 0
  748. str_align:
  749. db 'align'
  750. db 0
  751. str_extern:
  752. db 'extern'
  753. db 0
  754. str_equ:
  755. db 'equ'
  756. db 0
  757. str_decoding_line:
  758. db 'Decoding line: '
  759. db 0
  760. str_empty:
  761. db 0
  762. str_ass_finished1:
  763. db 'Finished assembling a file with '
  764. db 0
  765. str_ass_finished2:
  766. db ' lines!'
  767. db NEWLINE
  768. db 0
  769. str_symb_num1:
  770. db 'There are now '
  771. db 0
  772. str_symb_num2:
  773. db ' known symbols.'
  774. db NEWLINE
  775. db 0
  776. section .bss
  777. input_buf_ptr:
  778. resd 1
  779. section .text
  780. global get_input_buf
  781. get_input_buf:
  782. mov eax, input_buf_ptr
  783. mov eax, [eax]
  784. ret
  785. global get_opcode_names
  786. get_opcode_names:
  787. mov eax, opcode_names
  788. ret
  789. global get_opcode_funcs
  790. get_opcode_funcs:
  791. mov eax, opcode_funcs
  792. ret
  793. global get_rm32_opcode
  794. get_rm32_opcode:
  795. mov eax, rm32_opcode
  796. ret
  797. global get_imm32_opcode
  798. get_imm32_opcode:
  799. mov eax, imm32_opcode
  800. ret
  801. global get_rm8r8_opcode
  802. get_rm8r8_opcode:
  803. mov eax, rm8r8_opcode
  804. ret
  805. global get_rm32r32_opcode
  806. get_rm32r32_opcode:
  807. mov eax, rm32r32_opcode
  808. ret
  809. global get_r8rm8_opcode
  810. get_r8rm8_opcode:
  811. mov eax, r8rm8_opcode
  812. ret
  813. global get_r32rm32_opcode
  814. get_r32rm32_opcode:
  815. mov eax, r32rm32_opcode
  816. ret
  817. global get_rm8imm8_opcode
  818. get_rm8imm8_opcode:
  819. mov eax, rm8imm8_opcode
  820. ret
  821. global get_rm32imm32_opcode
  822. get_rm32imm32_opcode:
  823. mov eax, rm32imm32_opcode
  824. ret
  825. global assert
  826. assert:
  827. cmp DWORD [esp+4], 0
  828. jne assert_return
  829. call platform_panic
  830. assert_return:
  831. ret
  832. global readline
  833. readline:
  834. push ebp
  835. mov ebp, esp
  836. readline_begin_loop:
  837. ;; If len is zero, jump to panic
  838. cmp DWORD [ebp+16], 0
  839. je platform_panic
  840. ;; Call platform_read_char
  841. mov ecx, [ebp+8]
  842. push ecx
  843. call platform_read_char
  844. add esp, 4
  845. ;; Store the buffer address in edx
  846. mov edx, [ebp+12]
  847. ;; Handle newline and eof
  848. cmp eax, NEWLINE
  849. je readline_newline_found
  850. cmp eax, 0xffffffff
  851. je readline_eof_found
  852. ;; Copy a byte
  853. mov [edx], al
  854. ;; Increment the buffer and decrement the length
  855. add edx, 1
  856. mov [ebp+12], edx
  857. mov ecx, [ebp+16]
  858. sub ecx, 1
  859. mov [ebp+16], ecx
  860. jmp readline_begin_loop
  861. ;; On newline, store the string terminator and return 0
  862. readline_newline_found:
  863. mov BYTE [edx], 0
  864. mov eax, 0
  865. jmp readline_ret
  866. ;; On eof, store the string terminator and return 1
  867. readline_eof_found:
  868. mov BYTE [edx], 0
  869. mov eax, 1
  870. jmp readline_ret
  871. readline_ret:
  872. pop ebp
  873. ret
  874. global trimstr
  875. trimstr:
  876. ;; Load registers (eax for writing, ecx for reading)
  877. mov eax, [esp+4]
  878. mov ecx, eax
  879. ;; Skip the initial whitespace
  880. trimstr_skip_initial:
  881. cmp BYTE [ecx], SPACE
  882. je trimstr_initial_white
  883. cmp BYTE [ecx], TAB
  884. je trimstr_initial_white
  885. jmp trimstr_copy_loop
  886. trimstr_initial_white:
  887. add ecx, 1
  888. jmp trimstr_skip_initial
  889. ;; Copy until the string terminator
  890. trimstr_copy_loop:
  891. cmp BYTE [ecx], 0
  892. mov dl, [ecx]
  893. mov [eax], dl
  894. je trimstr_trim_end
  895. add ecx, 1
  896. add eax, 1
  897. jmp trimstr_copy_loop
  898. ;; Replace the final whitespace with terminators
  899. trimstr_trim_end:
  900. sub eax, 1
  901. trimstr_trim_loop2:
  902. cmp eax, [esp+4]
  903. jb trimstr_ret
  904. cmp BYTE [eax], SPACE
  905. je trimstr_final_white
  906. cmp BYTE [eax], TAB
  907. je trimstr_final_white
  908. jmp trimstr_ret
  909. trimstr_final_white:
  910. mov BYTE [eax], 0
  911. sub eax, 1
  912. jmp trimstr_trim_loop2
  913. trimstr_ret:
  914. ret
  915. global remove_spaces
  916. remove_spaces:
  917. ;; Load registers (eax for writing, ecx for reading)
  918. mov eax, [esp+4]
  919. mov ecx, eax
  920. ;; Main loop
  921. remove_spaces_loop:
  922. ;; Copy the byte and, if found terminator, stop
  923. cmp BYTE [ecx], 0
  924. mov dl, [ecx]
  925. mov [eax], dl
  926. je remove_spaces_ret
  927. ;; Advance the read pointer; advance the write pointer only if we
  928. ;; did not found whitespace
  929. add ecx, 1
  930. cmp dl, SPACE
  931. je remove_spaces_loop
  932. cmp dl, TAB
  933. je remove_spaces_loop
  934. add eax, 1
  935. jmp remove_spaces_loop
  936. remove_spaces_ret:
  937. ret
  938. global isstrpref
  939. isstrpref:
  940. ;; Load registers
  941. mov eax, [esp+4]
  942. mov ecx, [esp+8]
  943. isstrpref_loop:
  944. ;; If the first string is finished, then return 1
  945. mov dl, [eax]
  946. cmp dl, 0
  947. jne isstrpref_after_cmp1
  948. mov eax, 1
  949. ret
  950. isstrpref_after_cmp1:
  951. ;; If the characters do not match, return 0
  952. cmp dl, [ecx]
  953. je isstrpref_after_cmp2
  954. mov eax, 0
  955. ret
  956. isstrpref_after_cmp2:
  957. ;; Increment both pointers and restart
  958. add eax, 1
  959. add ecx, 1
  960. jmp isstrpref_loop
  961. global decode_reg32
  962. decode_reg32:
  963. ;; Save and load registers
  964. push ebx
  965. mov ebx, [esp+8]
  966. push esi
  967. ;; Compare the argument with each possible register name
  968. mov esi, 0
  969. push reg_eax
  970. push ebx
  971. call strcmp
  972. add esp, 8
  973. cmp eax, 0
  974. je decode_reg32_ret
  975. mov esi, 1
  976. push reg_ecx
  977. push ebx
  978. call strcmp
  979. add esp, 8
  980. cmp eax, 0
  981. je decode_reg32_ret
  982. mov esi, 2
  983. push reg_edx
  984. push ebx
  985. call strcmp
  986. add esp, 8
  987. cmp eax, 0
  988. je decode_reg32_ret
  989. mov esi, 3
  990. push reg_ebx
  991. push ebx
  992. call strcmp
  993. add esp, 8
  994. cmp eax, 0
  995. je decode_reg32_ret
  996. mov esi, 4
  997. push reg_esp
  998. push ebx
  999. call strcmp
  1000. add esp, 8
  1001. cmp eax, 0
  1002. je decode_reg32_ret
  1003. mov esi, 5
  1004. push reg_ebp
  1005. push ebx
  1006. call strcmp
  1007. add esp, 8
  1008. cmp eax, 0
  1009. je decode_reg32_ret
  1010. mov esi, 6
  1011. push reg_esi
  1012. push ebx
  1013. call strcmp
  1014. add esp, 8
  1015. cmp eax, 0
  1016. je decode_reg32_ret
  1017. mov esi, 7
  1018. push reg_edi
  1019. push ebx
  1020. call strcmp
  1021. add esp, 8
  1022. cmp eax, 0
  1023. je decode_reg32_ret
  1024. ;; Return -1 if none matched
  1025. mov esi, 0xffffffff
  1026. decode_reg32_ret:
  1027. mov eax, esi
  1028. pop esi
  1029. pop ebx
  1030. ret
  1031. global decode_reg8
  1032. decode_reg8:
  1033. ;; Save and load registers
  1034. push ebx
  1035. mov ebx, [esp+8]
  1036. push esi
  1037. ;; Compare the argument with each possible register name
  1038. mov esi, 0
  1039. push reg_al
  1040. push ebx
  1041. call strcmp
  1042. add esp, 8
  1043. cmp eax, 0
  1044. je decode_reg8_ret
  1045. mov esi, 1
  1046. push reg_cl
  1047. push ebx
  1048. call strcmp
  1049. add esp, 8
  1050. cmp eax, 0
  1051. je decode_reg8_ret
  1052. mov esi, 2
  1053. push reg_dl
  1054. push ebx
  1055. call strcmp
  1056. add esp, 8
  1057. cmp eax, 0
  1058. je decode_reg8_ret
  1059. mov esi, 3
  1060. push reg_bl
  1061. push ebx
  1062. call strcmp
  1063. add esp, 8
  1064. cmp eax, 0
  1065. je decode_reg8_ret
  1066. mov esi, 4
  1067. push reg_ah
  1068. push ebx
  1069. call strcmp
  1070. add esp, 8
  1071. cmp eax, 0
  1072. je decode_reg8_ret
  1073. mov esi, 5
  1074. push reg_ch
  1075. push ebx
  1076. call strcmp
  1077. add esp, 8
  1078. cmp eax, 0
  1079. je decode_reg8_ret
  1080. mov esi, 6
  1081. push reg_dh
  1082. push ebx
  1083. call strcmp
  1084. add esp, 8
  1085. cmp eax, 0
  1086. je decode_reg8_ret
  1087. mov esi, 7
  1088. push reg_bh
  1089. push ebx
  1090. call strcmp
  1091. add esp, 8
  1092. cmp eax, 0
  1093. je decode_reg8_ret
  1094. ;; Return -1 if none matched
  1095. mov esi, 0xffffffff
  1096. decode_reg8_ret:
  1097. mov eax, esi
  1098. pop esi
  1099. pop ebx
  1100. ret
  1101. global decode_number_or_symbol
  1102. decode_number_or_symbol:
  1103. push ebp
  1104. mov ebp, esp
  1105. ;; Call decode_number
  1106. mov eax, [ebp+12]
  1107. push eax
  1108. mov eax, [ebp+8]
  1109. push eax
  1110. call decode_number
  1111. add esp, 8
  1112. ;; If decode_number succeded, return 1
  1113. cmp eax, 1
  1114. jne decode_number_or_symbol_after_number
  1115. jmp decode_number_or_symbol_ret
  1116. decode_number_or_symbol_after_number:
  1117. ;; Branch to appropriate stage (in particular, if third argument is
  1118. ;; true assume stage 1)
  1119. mov edx, stage
  1120. mov eax, [edx]
  1121. cmp eax, 1
  1122. je decode_number_or_symbol_stage1
  1123. cmp DWORD [ebp+16], 0
  1124. jne decode_number_or_symbol_stage1
  1125. cmp eax, 0
  1126. je decode_number_or_symbol_stage0
  1127. jmp platform_panic
  1128. decode_number_or_symbol_stage0:
  1129. ;; Set the number to placeholder 0 and return 1
  1130. mov eax, [ebp+12]
  1131. mov DWORD [eax], 0
  1132. mov eax, 1
  1133. jmp decode_number_or_symbol_ret
  1134. decode_number_or_symbol_stage1:
  1135. ;; Call find_symbol and return what it returns
  1136. push 0
  1137. push DWORD [ebp+12]
  1138. push DWORD [ebp+8]
  1139. call find_symbol
  1140. add esp, 12
  1141. jmp decode_number_or_symbol_ret
  1142. decode_number_or_symbol_ret:
  1143. pop ebp
  1144. ret
  1145. global decode_operand
  1146. decode_operand:
  1147. push ebp
  1148. mov ebp, esp
  1149. push ebx
  1150. push esi
  1151. ;; Use ebx for the input string
  1152. mov ebx, [ebp+8]
  1153. ;; Call remove_spaces
  1154. push ebx
  1155. call remove_spaces
  1156. add esp, 4
  1157. ;; Use cl and ch to remember if we found 8 or 32 bits code
  1158. mov ecx, 0
  1159. ;; Search for BYTE prefix
  1160. push ecx
  1161. push ebx
  1162. push str_BYTE
  1163. call isstrpref
  1164. add esp, 8
  1165. pop ecx
  1166. cmp eax, 0
  1167. je decode_operand_after_byte_search
  1168. add ebx, 4
  1169. mov cl, 1
  1170. ;; Search for DWORD prefix
  1171. decode_operand_after_byte_search:
  1172. push ecx
  1173. push ebx
  1174. push str_DWORD
  1175. call isstrpref
  1176. add esp, 8
  1177. pop ecx
  1178. cmp eax, 0
  1179. je decode_operand_after_dword_search
  1180. add ebx, 5
  1181. mov ch, 1
  1182. ;; Check that at most one prefix was found
  1183. decode_operand_after_dword_search:
  1184. mov dl, cl
  1185. and dl, ch
  1186. cmp dl, 0
  1187. jne platform_panic
  1188. ;; Check whether the operand is direct or indirect
  1189. cmp BYTE [ebx], SQ_OPEN
  1190. jne decode_operand_direct
  1191. ;; Indirect operand: mark as such and consume character
  1192. mov edx, [ebp+12]
  1193. mov DWORD [edx], 0
  1194. add ebx, 1
  1195. ;; In this branch cl and ch are not used, so we can save them in the
  1196. ;; caller space and then recycle the register
  1197. mov edx, [ebp+24]
  1198. mov DWORD [edx], 0
  1199. mov [edx], cl
  1200. mov edx, [ebp+28]
  1201. mov DWORD [edx], 0
  1202. mov [edx], ch
  1203. ;; Search for the plus
  1204. push PLUS
  1205. push ebx
  1206. call find_char
  1207. add esp, 8
  1208. cmp eax, 0xffffffff
  1209. jne decode_operand_have_plus
  1210. ;; There is no plus, so the displacement is zero
  1211. mov edx, [ebp+20]
  1212. mov DWORD [edx], 0
  1213. ;; Search for the closed bracket
  1214. push SQ_CLOSED
  1215. push ebx
  1216. call find_char
  1217. add esp, 8
  1218. cmp eax, 0xffffffff
  1219. je decode_operand_ret_false
  1220. ;; Check that the following character is a terminator
  1221. mov ecx, ebx
  1222. add ecx, eax
  1223. cmp BYTE [ecx+1], 0
  1224. jne decode_operand_ret_false
  1225. ;; Overwrite the closed bracket with a terminator and recognize the
  1226. ;; register name (which must be a 32 bits register)
  1227. mov BYTE [ecx], 0
  1228. push ebx
  1229. call decode_reg32
  1230. add esp, 4
  1231. ;; Save its value in the caller space and return appropriately
  1232. mov edx, [ebp+16]
  1233. mov [edx], eax
  1234. cmp eax, 0xffffffff
  1235. je decode_operand_ret_false
  1236. jmp decode_operand_ret_true
  1237. decode_operand_have_plus:
  1238. ;; Overwrite the plus with a terminator and recognize the register
  1239. ;; name
  1240. mov esi, ebx
  1241. add esi, eax
  1242. mov BYTE [esi], 0
  1243. push ebx
  1244. call decode_reg32
  1245. add esp, 4
  1246. ;; Save the register in the caller space and return 0 if it failed
  1247. mov edx, [ebp+16]
  1248. mov [edx], eax
  1249. cmp eax, 0xffffffff
  1250. je decode_operand_ret_false
  1251. ;; Search for the closed bracket
  1252. mov ebx, esi
  1253. add ebx, 1
  1254. push SQ_CLOSED
  1255. push ebx
  1256. call find_char
  1257. add esp, 8
  1258. cmp eax, 0xffffffff
  1259. je decode_operand_ret_false
  1260. ;; Check that the following character is a terminator
  1261. mov ecx, ebx
  1262. add ecx, eax
  1263. cmp BYTE [ecx+1], 0
  1264. jne decode_operand_ret_false
  1265. ;; Overwrite the closed bracket with a terminator and recognized the
  1266. ;; displacement
  1267. mov BYTE [ecx], 0
  1268. push 0
  1269. mov eax, DWORD [ebp+20]
  1270. push eax
  1271. push ebx
  1272. call decode_number_or_symbol
  1273. add esp, 12
  1274. jmp decode_operand_ret
  1275. decode_operand_direct:
  1276. ;; Direct operand: save this fact in the caller space
  1277. mov edx, [ebp+12]
  1278. mov DWORD [edx], 1
  1279. ;; No prefix should have been found in this case
  1280. cmp ecx, 0
  1281. jne decode_operand_ret_false
  1282. ;; Try to recognized the operand as a 32 bits register
  1283. push ebx
  1284. call decode_reg32
  1285. add esp, 4
  1286. cmp eax, 0xffffffff
  1287. je decode_operand_8bit
  1288. ;; Save the register in the caller space
  1289. mov edx, [ebp+16]
  1290. mov [edx], eax
  1291. ;; Save the detected size in the caller space
  1292. mov edx, [ebp+24]
  1293. mov DWORD [edx], 0
  1294. mov edx, [ebp+28]
  1295. mov DWORD [edx], 1
  1296. jmp decode_operand_ret_true
  1297. decode_operand_8bit:
  1298. ;; Try to recognize the operand as a 8 bits register
  1299. push ebx
  1300. call decode_reg8
  1301. add esp, 4
  1302. cmp eax, 0xffffffff
  1303. je decode_operand_ret_false
  1304. ;; Save the register in the caller space
  1305. mov edx, [ebp+16]
  1306. mov [edx], eax
  1307. ;; Save the detected size in the caller space
  1308. mov edx, [ebp+24]
  1309. mov DWORD [edx], 1
  1310. mov edx, [ebp+28]
  1311. mov DWORD [edx], 0
  1312. jmp decode_operand_ret_true
  1313. decode_operand_ret_true:
  1314. mov eax, 1
  1315. jmp decode_operand_ret
  1316. decode_operand_ret_false:
  1317. mov eax, 0
  1318. jmp decode_operand_ret
  1319. decode_operand_ret:
  1320. pop esi
  1321. pop ebx
  1322. pop ebp
  1323. ret
  1324. global process_bss_line
  1325. process_bss_line:
  1326. ;; Check if the opcode is resb
  1327. mov edx, [esp+4]
  1328. push str_resb
  1329. push edx
  1330. call strcmp
  1331. add esp, 8
  1332. cmp eax, 0
  1333. je process_bss_line_resb
  1334. ;; Check is the opcode is resd
  1335. mov edx, [esp+4]
  1336. push str_resd
  1337. push edx
  1338. call strcmp
  1339. add esp, 8
  1340. cmp eax, 0
  1341. je process_bss_line_resd
  1342. mov eax, 0
  1343. ret
  1344. process_bss_line_resb:
  1345. ;; Save the argument before we mess up with the stack
  1346. mov edx, [esp+8]
  1347. ;; Push 0 to allocate a local variable and take its address
  1348. push 0
  1349. mov ecx, esp
  1350. ;; Call decode_number_or_symbol
  1351. push 1
  1352. push ecx
  1353. push edx
  1354. call decode_number_or_symbol
  1355. add esp, 12
  1356. ;; Deallocate the temporary variable and save it in ecx
  1357. pop ecx
  1358. cmp eax, 0
  1359. je platform_panic
  1360. process_bss_line_resb_loop:
  1361. ;; Loop ecx times calling emit(0) at each loop
  1362. cmp ecx, 0
  1363. je process_bss_line_ret
  1364. sub ecx, 1
  1365. push ecx
  1366. push 0
  1367. call emit
  1368. add esp, 4
  1369. pop ecx
  1370. jmp process_bss_line_resb_loop
  1371. ;; Everything as above, but with emit32 instead of emit
  1372. process_bss_line_resd:
  1373. mov edx, [esp+8]
  1374. push 0
  1375. mov ecx, esp
  1376. push 1
  1377. push ecx
  1378. push edx
  1379. call decode_number_or_symbol
  1380. add esp, 12
  1381. pop ecx
  1382. cmp eax, 0
  1383. je platform_panic
  1384. process_bss_line_resd_loop:
  1385. cmp ecx, 0
  1386. je process_bss_line_ret
  1387. sub ecx, 1
  1388. push ecx
  1389. push 0
  1390. call emit32
  1391. add esp, 4
  1392. pop ecx
  1393. jmp process_bss_line_resd_loop
  1394. process_bss_line_ret:
  1395. mov eax, 1
  1396. ret
  1397. global process_data_line
  1398. process_data_line:
  1399. ;; Check if the opcode is db
  1400. mov edx, [esp+4]
  1401. push str_db
  1402. push edx
  1403. call strcmp
  1404. add esp, 8
  1405. cmp eax, 0
  1406. je process_data_line_db
  1407. ;; Check is the opcode is dd
  1408. mov edx, [esp+4]
  1409. push str_dd
  1410. push edx
  1411. call strcmp
  1412. add esp, 8
  1413. cmp eax, 0
  1414. je process_data_line_dd
  1415. mov eax, 0
  1416. ret
  1417. process_data_line_db:
  1418. ;; If data begin with an apex, treat it as a string
  1419. mov edx, [esp+8]
  1420. cmp BYTE [edx], APEX
  1421. je process_data_line_string
  1422. ;; If not, treat it as a single 8 bits value
  1423. mov eax, 0
  1424. jmp process_data_line_value
  1425. process_data_line_dd:
  1426. ;; Assume data is a single 32 bits value
  1427. mov edx, [esp+8]
  1428. mov eax, 1
  1429. jmp process_data_line_value
  1430. process_data_line_value:
  1431. ;; Like process_bss_line_resb, but with just one emit at the end
  1432. ;; (and decode_number_or_symbol is permitted to fail in stage 0)
  1433. push eax
  1434. push 0
  1435. mov ecx, esp
  1436. push 0
  1437. push ecx
  1438. push edx
  1439. call decode_number_or_symbol
  1440. add esp, 12
  1441. pop ecx
  1442. cmp eax, 0
  1443. je platform_panic
  1444. ;; We used eax to remember if data is 8 or 32 bits; call emit or
  1445. ;; emit32 accordingly
  1446. pop eax
  1447. cmp eax, 0
  1448. jne process_data_line_emit32
  1449. push ecx
  1450. call emit
  1451. add esp, 4
  1452. jmp process_data_line_ret
  1453. process_data_line_emit32:
  1454. push ecx
  1455. call emit32
  1456. add esp, 4
  1457. jmp process_data_line_ret
  1458. process_data_line_string:
  1459. ;; Compute string length
  1460. push edx
  1461. push edx
  1462. call strlen
  1463. add esp, 4
  1464. pop edx
  1465. ;; Check that data has at least length 2 (the two apices)
  1466. cmp eax, 2
  1467. jnae platform_panic
  1468. ;; Check that data has an apex at the end
  1469. mov ecx, edx
  1470. add ecx, eax
  1471. sub ecx, 1
  1472. cmp BYTE [ecx], APEX
  1473. jne platform_panic
  1474. ;; Consume the first apex and overwrite the last with a terminator
  1475. mov BYTE [ecx], 0
  1476. add edx, 1
  1477. ;; Emit all the bytes
  1478. process_data_line_dd_loop:
  1479. cmp BYTE [edx], 0
  1480. je process_data_line_ret
  1481. push edx
  1482. mov ecx, 0
  1483. mov cl, BYTE [edx]
  1484. push ecx
  1485. call emit
  1486. add esp, 4
  1487. pop edx
  1488. add edx, 1
  1489. jmp process_data_line_dd_loop
  1490. process_data_line_ret:
  1491. mov eax, 1
  1492. ret
  1493. global emit_modrm
  1494. emit_modrm:
  1495. ;; Check that input do not overlap when being shifted in place
  1496. mov eax, 0x3
  1497. and eax, [esp+4]
  1498. cmp eax, [esp+4]
  1499. jne platform_panic
  1500. mov eax, 0x7
  1501. and eax, [esp+8]
  1502. cmp eax, [esp+8]
  1503. jne platform_panic
  1504. mov eax, 0x7
  1505. and eax, [esp+12]
  1506. cmp eax, [esp+12]
  1507. jne platform_panic
  1508. ;; Only support a direct register, or an indirect register + disp32
  1509. cmp BYTE [esp+4], 0
  1510. je platform_panic
  1511. cmp BYTE [esp+4], 1
  1512. je platform_panic
  1513. ;; Assemble the first byte
  1514. mov eax, 0
  1515. mov al, BYTE [esp+4]
  1516. mov edx, 8
  1517. mul edx
  1518. add al, BYTE [esp+8]
  1519. mov edx, 8
  1520. mul edx
  1521. add al, BYTE [esp+12]
  1522. ;; Emit the first byte
  1523. push eax
  1524. call emit
  1525. add esp, 4
  1526. ;; In the particular case of ESP used as indirect base, a SIB is
  1527. ;; needed
  1528. cmp BYTE [esp+4], 2
  1529. jne emit_modrm_ret
  1530. cmp BYTE [esp+12], 4
  1531. jne emit_modrm_ret
  1532. push 0x24
  1533. call emit
  1534. add esp, 4
  1535. emit_modrm_ret:
  1536. ret
  1537. global emit_helper
  1538. emit_helper:
  1539. push ebp
  1540. mov ebp, esp
  1541. ;; Check the opcode is valid and call first emit
  1542. mov ecx, [ebp+8]
  1543. mov edx, 0
  1544. mov dl, cl
  1545. cmp cl, 0xf0
  1546. je platform_panic
  1547. push edx
  1548. call emit
  1549. add esp, 4
  1550. ;; Perhaps call second emit
  1551. mov ecx, [ebp+8]
  1552. and ecx, 0xff0000
  1553. cmp ecx, 0
  1554. je emit_helper_modrm
  1555. mov ecx, [ebp+8]
  1556. mov edx, 0
  1557. mov dl, ch
  1558. push edx
  1559. call emit
  1560. add esp, 4
  1561. emit_helper_modrm:
  1562. ;; Perhaps call emit_modrm
  1563. mov eax, [ebp+20]
  1564. cmp eax, 0xffffffff
  1565. je emit_helper_disp
  1566. push eax
  1567. mov edx, [ebp+16]
  1568. cmp edx, 0xffffffff
  1569. jne emit_helper_modrm3
  1570. mov ecx, [ebp+8]
  1571. mov edx, 0
  1572. mov dl, ch
  1573. emit_helper_modrm3:
  1574. push edx
  1575. mov ecx, 2
  1576. cmp DWORD [ebp+12], 0
  1577. je emit_helper_modrm2
  1578. mov ecx, 3
  1579. emit_helper_modrm2:
  1580. push ecx
  1581. call emit_modrm
  1582. add esp, 12
  1583. emit_helper_disp:
  1584. ;; Perhaps call emit32
  1585. cmp DWORD [ebp+12], 0
  1586. jne emit_helper_end
  1587. mov edx, [ebp+24]
  1588. push edx
  1589. call emit32
  1590. add esp, 4
  1591. emit_helper_end:
  1592. pop ebp
  1593. ret
  1594. global process_jmp_like
  1595. process_jmp_like:
  1596. push ebp
  1597. mov ebp, esp
  1598. ;; Allocate space for 5 variables:
  1599. ;; [ebp-4], which is [ebp+0xfffffffc]: is_direct
  1600. ;; [ebp-8], which is [ebp+0xfffffff8]: reg
  1601. ;; [ebp-12], whch is [ebp+0xfffffff4]: disp
  1602. ;; [ebp-16], which is [ebp+0xfffffff0]: is8
  1603. ;; [ebp-20], which is [ebp+0xffffffec]: is32
  1604. sub esp, 20
  1605. ;; Call decode_operand
  1606. mov eax, ebp
  1607. sub eax, 20
  1608. push eax
  1609. mov eax, ebp
  1610. sub eax, 16
  1611. push eax
  1612. mov eax, ebp
  1613. sub eax, 12
  1614. push eax
  1615. mov eax, ebp
  1616. sub eax, 8
  1617. push eax
  1618. mov eax, ebp
  1619. sub eax, 4
  1620. push eax
  1621. mov eax, [ebp+12]
  1622. push eax
  1623. call decode_operand
  1624. add esp, 24
  1625. cmp eax, 0
  1626. jne process_jmp_like_rm32
  1627. jmp process_jmp_like_rel32
  1628. process_jmp_like_rm32:
  1629. ;; Check the operand is not 8 bits
  1630. cmp DWORD [ebp+0xfffffff0], 0
  1631. jne platform_panic
  1632. ;; Get the opcode data
  1633. mov eax, [ebp+8]
  1634. mov edx, 4
  1635. mul edx
  1636. add eax, rm32_opcode
  1637. mov ecx, [eax]
  1638. ;; Call emit_helper
  1639. mov edx, [ebp+0xfffffff4]
  1640. push edx
  1641. mov edx, [ebp+0xfffffff8]
  1642. push edx
  1643. push 0xffffffff
  1644. mov edx, [ebp+0xfffffffc]
  1645. push edx
  1646. push ecx
  1647. call emit_helper
  1648. add esp, 20
  1649. jmp process_jmp_like_end
  1650. process_jmp_like_rel32:
  1651. ;; Get the opcode data
  1652. mov eax, [ebp+8]
  1653. mov edx, 4
  1654. mul edx
  1655. add eax, imm32_opcode
  1656. mov ecx, [eax]
  1657. ;; Call emit_helper
  1658. push 0
  1659. push 0xffffffff
  1660. push 0xffffffff
  1661. push 1
  1662. push ecx
  1663. call emit_helper
  1664. add esp, 20
  1665. ;; Call decode_number_or_symbol
  1666. push 0
  1667. mov edx, esp
  1668. push 0
  1669. push edx
  1670. mov edx, [ebp+12]
  1671. push edx
  1672. call decode_number_or_symbol
  1673. add esp, 12
  1674. ;; Check for success
  1675. cmp eax, 0
  1676. je platform_panic
  1677. ;; Store the value in edx and make it relative
  1678. pop edx
  1679. mov ecx, current_loc
  1680. sub edx, [ecx]
  1681. sub edx, 4
  1682. ;; Call emit32
  1683. push edx
  1684. call emit32
  1685. add esp, 4
  1686. jmp process_jmp_like_end
  1687. process_jmp_like_end:
  1688. add esp, 20
  1689. pop ebp
  1690. ret
  1691. global process_push_like
  1692. process_push_like:
  1693. push ebp
  1694. mov ebp, esp
  1695. ;; Allocate space for 5 variables:
  1696. ;; [ebp-4], which is [ebp+0xfffffffc]: is_direct
  1697. ;; [ebp-8], which is [ebp+0xfffffff8]: reg
  1698. ;; [ebp-12], whch is [ebp+0xfffffff4]: disp
  1699. ;; [ebp-16], which is [ebp+0xfffffff0]: is8
  1700. ;; [ebp-20], which is [ebp+0xffffffec]: is32
  1701. sub esp, 20
  1702. ;; Check if the operation is a bit shift
  1703. cmp DWORD [ebp+8], OP_SHL
  1704. je process_push_like_shift
  1705. cmp DWORD [ebp+8], OP_SHR
  1706. je process_push_like_shift
  1707. cmp DWORD [ebp+8], OP_SAL
  1708. je process_push_like_shift
  1709. cmp DWORD [ebp+8], OP_SAR
  1710. je process_push_like_shift
  1711. jmp process_push_like_decode
  1712. process_push_like_shift:
  1713. ;; Find the comma
  1714. push COMMA
  1715. mov edx, [ebp+12]
  1716. push edx
  1717. call find_char
  1718. add esp, 8
  1719. cmp eax, 0xffffffff
  1720. je platform_panic
  1721. ;; Substitute the comma with a terminator
  1722. mov ecx, [ebp+12]
  1723. add ecx, eax
  1724. mov BYTE [ecx], 0
  1725. ;; Trim second operand
  1726. add ecx, 1
  1727. push ecx
  1728. push ecx
  1729. call trimstr
  1730. add esp, 4
  1731. pop ecx
  1732. ;; Check that second operand is cl
  1733. push ecx
  1734. push reg_cl
  1735. call strcmp
  1736. add esp, 8
  1737. cmp eax, 0
  1738. jne platform_panic
  1739. process_push_like_decode:
  1740. ;; Call decode_operand
  1741. mov eax, ebp
  1742. sub eax, 20
  1743. push eax
  1744. mov eax, ebp
  1745. sub eax, 16
  1746. push eax
  1747. mov eax, ebp
  1748. sub eax, 12
  1749. push eax
  1750. mov eax, ebp
  1751. sub eax, 8
  1752. push eax
  1753. mov eax, ebp
  1754. sub eax, 4
  1755. push eax
  1756. mov eax, [ebp+12]
  1757. push eax
  1758. call decode_operand
  1759. add esp, 24
  1760. cmp eax, 0
  1761. jne process_push_like_rm32
  1762. jmp process_push_like_imm32
  1763. process_push_like_rm32:
  1764. ;; Check the operand is not 8 bits
  1765. cmp DWORD [ebp+0xfffffff0], 0
  1766. jne platform_panic
  1767. ;; Get the opcode data
  1768. mov eax, [ebp+8]
  1769. mov edx, 4
  1770. mul edx
  1771. add eax, rm32_opcode
  1772. mov ecx, [eax]
  1773. ;; Call emit_helper
  1774. mov edx, [ebp+0xfffffff4]
  1775. push edx
  1776. mov edx, [ebp+0xfffffff8]
  1777. push edx
  1778. push 0xffffffff
  1779. mov edx, [ebp+0xfffffffc]
  1780. push edx
  1781. push ecx
  1782. call emit_helper
  1783. add esp, 20
  1784. jmp process_push_like_end
  1785. process_push_like_imm32:
  1786. ;; Check that the operation is push
  1787. cmp DWORD [ebp+8], OP_PUSH
  1788. jne platform_panic
  1789. ;; Emit the operand
  1790. push 0x68
  1791. call emit
  1792. add esp, 4
  1793. ;; Call decode_number_or_symbol
  1794. push 0
  1795. mov edx, esp
  1796. push 0
  1797. push edx
  1798. mov edx, [ebp+12]
  1799. push edx
  1800. call decode_number_or_symbol
  1801. add esp, 12
  1802. cmp eax, 0
  1803. je platform_panic
  1804. ;; Call emit32
  1805. pop edx
  1806. push edx
  1807. call emit32
  1808. add esp, 4
  1809. jmp process_push_like_end
  1810. process_push_like_end:
  1811. add esp, 20
  1812. pop ebp
  1813. ret
  1814. global process_add_like
  1815. process_add_like:
  1816. push ebp
  1817. mov ebp, esp
  1818. ;; Allocate a lot of local variables
  1819. ;; [ebp-4], which is [ebp+0xfffffffc]: dest_is_direct
  1820. ;; [ebp-8], which is [ebp+0xfffffff8]: dest_reg
  1821. ;; [ebp-12], whch is [ebp+0xfffffff4]: dest_disp
  1822. ;; [ebp-16], which is [ebp+0xfffffff0]: dest_is8
  1823. ;; [ebp-20], which is [ebp+0xffffffec]: dest_is32
  1824. ;; [ebp-24], which is [ebp+0xffffffe8]: src_is_direct
  1825. ;; [ebp-28], which is [ebp+0xffffffe4]: src_reg
  1826. ;; [ebp-32], which is [ebp+0xffffffe0]: src_disp
  1827. ;; [ebp-36], which is [ebp+0xffffffdc]: src_is8
  1828. ;; [ebp-40], which is [ebo+0xffffffd8]: src_is32
  1829. sub esp, 40
  1830. ;; Find the comma
  1831. push COMMA
  1832. mov edx, [ebp+12]
  1833. push edx
  1834. call find_char
  1835. add esp, 8
  1836. cmp eax, 0xffffffff
  1837. je platform_panic
  1838. ;; Substitute the comma with a terminator
  1839. mov ecx, [ebp+12]
  1840. add ecx, eax
  1841. mov BYTE [ecx], 0
  1842. ;; Push following position on the stack
  1843. add ecx, 1
  1844. push ecx
  1845. ;; Call decode_operand for destination
  1846. mov ecx, ebp
  1847. sub ecx, 20
  1848. push ecx
  1849. mov ecx, ebp
  1850. sub ecx, 16
  1851. push ecx
  1852. mov ecx, ebp
  1853. sub ecx, 12
  1854. push ecx
  1855. mov ecx, ebp
  1856. sub ecx, 8
  1857. push ecx
  1858. mov ecx, ebp
  1859. sub ecx, 4
  1860. push ecx
  1861. mov ecx, [ebp+12]
  1862. push ecx
  1863. call decode_operand
  1864. add esp, 24
  1865. ;; Panic if decoding failed
  1866. cmp eax, 0
  1867. je platform_panic
  1868. ;; Call decode_operand for source
  1869. pop edx
  1870. push edx
  1871. mov ecx, ebp
  1872. sub ecx, 40
  1873. push ecx
  1874. mov ecx, ebp
  1875. sub ecx, 36
  1876. push ecx
  1877. mov ecx, ebp
  1878. sub ecx, 32
  1879. push ecx
  1880. mov ecx, ebp
  1881. sub ecx, 28
  1882. push ecx
  1883. mov ecx, ebp
  1884. sub ecx, 24
  1885. push ecx
  1886. push edx
  1887. call decode_operand
  1888. add esp, 24
  1889. pop edx
  1890. cmp eax, 0
  1891. je process_add_like_imm
  1892. ;; Decide whether this is an 8 or 32 bits operation
  1893. mov dl, [ebp+0xfffffff0]
  1894. or dl, [ebp+0xffffffdc]
  1895. mov dh, [ebp+0xffffffec]
  1896. or dh, [ebp+0xffffffd8]
  1897. ;; Check that the situation is consistent
  1898. mov al, dl
  1899. or al, dh
  1900. cmp al, 0
  1901. je platform_panic
  1902. mov al, dl
  1903. and al, dh
  1904. cmp al, 0
  1905. jne platform_panic
  1906. ;; Split depending on whether destination is direct or not
  1907. mov ecx, [ebp+0xfffffffc]
  1908. cmp ecx, 0
  1909. jne process_add_like_dest_direct
  1910. jmp process_add_like_dest_indirect
  1911. process_add_like_dest_direct:
  1912. ;; Split depending on 8 or 32 bits operation
  1913. cmp dl, 0
  1914. jne process_add_like_dest_direct_8
  1915. jmp process_add_like_dest_direct_32
  1916. process_add_like_dest_direct_8:
  1917. ;; Retrieve opcode_data
  1918. mov eax, [ebp+8]
  1919. mov edx, 4
  1920. mul edx
  1921. add eax, r8rm8_opcode
  1922. mov ecx, [eax]
  1923. ;; Call emit_helper
  1924. mov eax, [ebp+0xffffffe0]
  1925. push eax
  1926. mov eax, [ebp+0xffffffe4]
  1927. push eax
  1928. mov eax, [ebp+0xfffffff8]
  1929. push eax
  1930. mov eax, [ebp+0xffffffe8]
  1931. push eax
  1932. push ecx
  1933. call emit_helper
  1934. add esp, 20
  1935. jmp process_add_like_end
  1936. process_add_like_dest_direct_32:
  1937. ;; Retrieve opcode_data
  1938. mov eax, [ebp+8]
  1939. mov edx, 4
  1940. mul edx
  1941. add eax, r32rm32_opcode
  1942. mov ecx, [eax]
  1943. ;; Call emit_helper
  1944. mov eax, [ebp+0xffffffe0]
  1945. push eax
  1946. mov eax, [ebp+0xffffffe4]
  1947. push eax
  1948. mov eax, [ebp+0xfffffff8]
  1949. push eax
  1950. mov eax, [ebp+0xffffffe8]
  1951. push eax
  1952. push ecx
  1953. call emit_helper
  1954. add esp, 20
  1955. jmp process_add_like_end
  1956. process_add_like_dest_indirect:
  1957. ;; Check that source is direct
  1958. cmp DWORD [ebp+0xffffffe8], 0
  1959. je platform_panic
  1960. ;; Split depending on 8 or 32 bits operation
  1961. cmp dl, 0
  1962. jne process_add_like_dest_indirect_8
  1963. jmp process_add_like_dest_indirect_32
  1964. process_add_like_dest_indirect_8:
  1965. ;; Retrieve opcode_data
  1966. mov eax, [ebp+8]
  1967. mov edx, 4
  1968. mul edx
  1969. add eax, rm8r8_opcode
  1970. mov ecx, [eax]
  1971. ;; Call emit_helper
  1972. mov eax, [ebp+0xfffffff4]
  1973. push eax
  1974. mov eax, [ebp+0xfffffff8]
  1975. push eax
  1976. mov eax, [ebp+0xffffffe4]
  1977. push eax
  1978. push 0
  1979. push ecx
  1980. call emit_helper
  1981. add esp, 20
  1982. jmp process_add_like_end
  1983. process_add_like_dest_indirect_32:
  1984. ;; Retrieve opcode_data
  1985. mov eax, [ebp+8]
  1986. mov edx, 4
  1987. mul edx
  1988. add eax, rm32r32_opcode
  1989. mov ecx, [eax]
  1990. ;; Call emit_helper
  1991. mov eax, [ebp+0xfffffff4]
  1992. push eax
  1993. mov eax, [ebp+0xfffffff8]
  1994. push eax
  1995. mov eax, [ebp+0xffffffe4]
  1996. push eax
  1997. push 0
  1998. push ecx
  1999. call emit_helper
  2000. add esp, 20
  2001. jmp process_add_like_end
  2002. process_add_like_imm:
  2003. ;; Check that we know the operation size
  2004. mov eax, [ebp+0xfffffff0]
  2005. or eax, [ebp+0xffffffec]
  2006. cmp eax, 0
  2007. je platform_panic
  2008. ;; Call decode_number_or_symbol
  2009. push 0
  2010. mov ecx, esp
  2011. push 0
  2012. push ecx
  2013. push edx
  2014. call decode_number_or_symbol
  2015. add esp, 12
  2016. pop edx
  2017. ;; Check it did work
  2018. cmp eax, 0
  2019. je platform_panic
  2020. cmp DWORD [ebp+0xfffffff0], 0
  2021. je process_add_like_imm_32
  2022. jmp process_add_like_imm_8
  2023. process_add_like_imm_8:
  2024. push edx
  2025. ;; Retrieve opcode_data
  2026. mov eax, [ebp+8]
  2027. mov edx, 4
  2028. mul edx
  2029. add eax, rm8imm8_opcode
  2030. mov ecx, [eax]
  2031. ;; Call emit_helper
  2032. mov eax, [ebp+0xfffffff4]
  2033. push eax
  2034. mov eax, [ebp+0xfffffff8]
  2035. push eax
  2036. push 0xffffffff
  2037. mov eax, [ebp+0xfffffffc]
  2038. push eax
  2039. push ecx
  2040. call emit_helper
  2041. add esp, 20
  2042. ;; Call emit
  2043. pop edx
  2044. push edx
  2045. call emit
  2046. add esp, 4
  2047. jmp process_add_like_end
  2048. process_add_like_imm_32:
  2049. push edx
  2050. ;; Retrieve opcode_data
  2051. mov eax, [ebp+8]
  2052. mov edx, 4
  2053. mul edx
  2054. add eax, rm32imm32_opcode
  2055. mov ecx, [eax]
  2056. ;; Call emit_helper
  2057. mov eax, [ebp+0xfffffff4]
  2058. push eax
  2059. mov eax, [ebp+0xfffffff8]
  2060. push eax
  2061. push 0xffffffff
  2062. mov eax, [ebp+0xfffffffc]
  2063. push eax
  2064. push ecx
  2065. call emit_helper
  2066. add esp, 20
  2067. ;; Call emit
  2068. pop edx
  2069. push edx
  2070. call emit32
  2071. add esp, 4
  2072. jmp process_add_like_end
  2073. process_add_like_end:
  2074. add esp, 40
  2075. pop ebp
  2076. ret
  2077. global process_int
  2078. process_int:
  2079. ;; Check the operation is actually an int
  2080. cmp DWORD [esp+4], OP_INT
  2081. jne platform_panic
  2082. ;; Call decode_number_or_symbol
  2083. push 0
  2084. mov edx, esp
  2085. push 0
  2086. push edx
  2087. mov edx, [esp+8]
  2088. push edx
  2089. call decode_number_or_symbol
  2090. add esp, 12
  2091. pop edx
  2092. ;; Check result
  2093. cmp eax, 0
  2094. je platform_panic
  2095. ;; Check the interrupt number is smaller than 0x100
  2096. cmp edx, 0x100
  2097. jnb platform_panic
  2098. ;; Call emit twice
  2099. push edx
  2100. push 0xcd
  2101. call emit
  2102. add esp, 4
  2103. call emit
  2104. add esp, 4
  2105. ret
  2106. global process_ret_like
  2107. process_ret_like:
  2108. ;; Get the opcode data
  2109. mov eax, [esp+4]
  2110. mov edx, 4
  2111. mul edx
  2112. add eax, empty_opcode
  2113. mov ecx, [eax]
  2114. ;; Check that data is empty
  2115. mov edx, [esp+8]
  2116. cmp BYTE [edx], 0
  2117. jne platform_panic
  2118. ;; Call emit_helper
  2119. push 0
  2120. push 0xffffffff
  2121. push 0xffffffff
  2122. push 1
  2123. push ecx
  2124. call emit_helper
  2125. add esp, 20
  2126. ret
  2127. global process_hlt
  2128. process_hlt:
  2129. ;; Check the operation is actually a ret
  2130. cmp DWORD [esp+4], OP_HLT
  2131. jne platform_panic
  2132. ;; Check that data is empty
  2133. mov edx, [esp+8]
  2134. cmp BYTE [edx], 0
  2135. jne platform_panic
  2136. ;; Call emit
  2137. push 0xf4
  2138. call emit
  2139. add esp, 4
  2140. ret
  2141. global process_in_like
  2142. process_in_like:
  2143. ;; Check the operation is valid
  2144. cmp DWORD [esp+4], OP_IN
  2145. je process_in_like_find_comma
  2146. cmp DWORD [esp+4], OP_OUT
  2147. je process_in_like_find_comma
  2148. call platform_panic
  2149. process_in_like_find_comma:
  2150. ;; Search the comma and panic if it is not there
  2151. mov eax, [esp+8]
  2152. push COMMA
  2153. push eax
  2154. call find_char
  2155. add esp, 8
  2156. cmp eax, 0xffffffff
  2157. je platform_panic
  2158. ;; Substitute the comma with a terminator
  2159. mov edx, [esp+8]
  2160. mov ecx, edx
  2161. add edx, eax
  2162. mov BYTE [edx], 0
  2163. add edx, 1
  2164. mov eax, ecx
  2165. ;; Decide which operation to use
  2166. cmp DWORD [esp+4], OP_IN
  2167. je process_in_like_in
  2168. jmp process_in_like_out
  2169. process_in_like_in:
  2170. ;; Leave the port operand in edx, the register operand in eax and
  2171. ;; the opcode in ecx
  2172. mov ecx, 0xec
  2173. jmp process_in_like_trim
  2174. process_in_like_out:
  2175. ;; Same as above
  2176. mov ecx, eax
  2177. mov eax, edx
  2178. mov edx, ecx
  2179. mov ecx, 0xee
  2180. jmp process_in_like_trim
  2181. process_in_like_trim:
  2182. ;; Trim both operands
  2183. push eax
  2184. push ecx
  2185. push edx
  2186. push eax
  2187. call trimstr
  2188. add esp, 4
  2189. pop edx
  2190. push edx
  2191. push edx
  2192. call trimstr
  2193. add esp, 4
  2194. pop edx
  2195. pop ecx
  2196. pop eax
  2197. ;; Check that the port operand is dx
  2198. push eax
  2199. push ecx
  2200. push reg_dx
  2201. push edx
  2202. call strcmp
  2203. add esp, 8
  2204. cmp eax, 0
  2205. jne platform_panic
  2206. pop ecx
  2207. pop eax
  2208. ;; Select depending on the register operand
  2209. push eax
  2210. push ecx
  2211. push reg_al
  2212. push eax
  2213. call strcmp
  2214. add esp, 8
  2215. cmp eax, 0
  2216. pop ecx
  2217. pop eax
  2218. je process_in_like_al
  2219. push eax
  2220. push ecx
  2221. push reg_ax
  2222. push eax
  2223. call strcmp
  2224. add esp, 8
  2225. cmp eax, 0
  2226. pop ecx
  2227. pop eax
  2228. je process_in_like_ax
  2229. push eax
  2230. push ecx
  2231. push reg_eax
  2232. push eax
  2233. call strcmp
  2234. add esp, 8
  2235. cmp eax, 0
  2236. pop ecx
  2237. pop eax
  2238. je process_in_like_eax
  2239. ;; Nothing matched, panic!
  2240. call platform_panic
  2241. process_in_like_al:
  2242. ;; Emit the opcode
  2243. push ecx
  2244. call emit
  2245. add esp, 4
  2246. jmp process_in_like_ret
  2247. process_in_like_ax:
  2248. ;; Emit the opcode
  2249. add ecx, 1
  2250. push ecx
  2251. push 0x66
  2252. call emit
  2253. add esp, 4
  2254. call emit
  2255. add esp, 4
  2256. jmp process_in_like_ret
  2257. process_in_like_eax:
  2258. add ecx, 1
  2259. push ecx
  2260. call emit
  2261. add esp, 4
  2262. jmp process_in_like_ret
  2263. process_in_like_ret:
  2264. ret
  2265. global process_text_line
  2266. process_text_line:
  2267. push ebp
  2268. mov ebp, esp
  2269. push esi
  2270. push edi
  2271. ;; Init esi for storing the current name and edi for counting
  2272. mov esi, opcode_names
  2273. mov edi, 0
  2274. process_text_line_loop:
  2275. ;; Check for termination: we did not find any match
  2276. mov eax, 0
  2277. cmp BYTE [esi], 0
  2278. je process_text_line_end
  2279. ;; Check for termination: we found a match
  2280. mov ecx, [ebp+8]
  2281. push ecx
  2282. push esi
  2283. call strcmp
  2284. add esp, 8
  2285. cmp eax, 0
  2286. je process_text_line_match
  2287. ;; Consume the string and increment the index
  2288. push esi
  2289. call strlen
  2290. add esp, 4
  2291. add esi, eax
  2292. add esi, 1
  2293. add edi, 1
  2294. jmp process_text_line_loop
  2295. process_text_line_match:
  2296. ;; Select the opcode function
  2297. mov eax, 4
  2298. mul edi
  2299. add eax, opcode_funcs
  2300. ;; Call the opcode function
  2301. mov edx, [ebp+12]
  2302. push edx
  2303. push edi
  2304. call [eax]
  2305. add esp, 8
  2306. mov eax, 1
  2307. jmp process_text_line_end
  2308. process_text_line_end:
  2309. pop edi
  2310. pop esi
  2311. pop ebp
  2312. ret
  2313. global process_directive_line
  2314. process_directive_line:
  2315. ;; Ignore section, org, bits, global and align
  2316. mov eax, [esp+4]
  2317. push str_section
  2318. push eax
  2319. call strcmp
  2320. add esp, 8
  2321. cmp eax, 0
  2322. je process_directive_line_ret_true
  2323. mov eax, [esp+4]
  2324. push str_org
  2325. push eax
  2326. call strcmp
  2327. add esp, 8
  2328. cmp eax, 0
  2329. je process_directive_line_ret_true
  2330. mov eax, [esp+4]
  2331. push str_bits
  2332. push eax
  2333. call strcmp
  2334. add esp, 8
  2335. cmp eax, 0
  2336. je process_directive_line_ret_true
  2337. mov eax, [esp+4]
  2338. push str_global
  2339. push eax
  2340. call strcmp
  2341. add esp, 8
  2342. cmp eax, 0
  2343. je process_directive_line_ret_true
  2344. mov eax, [esp+4]
  2345. push str_align
  2346. push eax
  2347. call strcmp
  2348. add esp, 8
  2349. cmp eax, 0
  2350. je process_directive_line_align
  2351. ;; Recognize extern
  2352. mov eax, [esp+4]
  2353. push str_extern
  2354. push eax
  2355. call strcmp
  2356. add esp, 8
  2357. cmp eax, 0
  2358. je process_directive_line_extern
  2359. ;; Return false for everything else
  2360. mov eax, 0
  2361. ret
  2362. process_directive_line_align:
  2363. ;; Call decode_number_or_symbol
  2364. mov eax, [esp+8]
  2365. push 0
  2366. mov ecx, esp
  2367. push 1
  2368. push ecx
  2369. push eax
  2370. call decode_number_or_symbol
  2371. add esp, 12
  2372. pop ecx
  2373. ;; Panic if it failed
  2374. cmp eax, 0
  2375. je platform_panic
  2376. ;; Compute the number of bytes to skip
  2377. mov edx, current_loc
  2378. mov eax, [edx]
  2379. mov edx, 0
  2380. div ecx
  2381. cmp edx, 0
  2382. je process_directive_line_ret_true
  2383. sub ecx, edx
  2384. ;; Skip them
  2385. process_directive_line_align_loop:
  2386. cmp ecx, 0
  2387. je process_directive_line_ret_true
  2388. push ecx
  2389. push 0
  2390. call emit
  2391. add esp, 4
  2392. pop ecx
  2393. sub ecx, 1
  2394. jmp process_directive_line_align_loop
  2395. process_directive_line_extern:
  2396. ;; Add a mock symbol
  2397. mov eax, [esp+8]
  2398. push 0xffffffff
  2399. push 0
  2400. push eax
  2401. call add_symbol_wrapper
  2402. add esp, 12
  2403. jmp process_directive_line_ret_true
  2404. process_directive_line_ret_true:
  2405. mov eax, 1
  2406. ret
  2407. global process_equ_line
  2408. process_equ_line:
  2409. ;; Find the space in data
  2410. mov eax, [esp+8]
  2411. push SPACE
  2412. push eax
  2413. call find_char
  2414. add esp, 8
  2415. ;; Fail if there is not one
  2416. cmp eax, 0xffffffff
  2417. je process_equ_line_ret_false
  2418. ;; Substitute it with a terminator and save the following position
  2419. mov edx, [esp+8]
  2420. add eax, edx
  2421. mov BYTE [eax], 0
  2422. mov ecx, eax
  2423. add eax, 1
  2424. push eax
  2425. ;; Check we are dealing with an equ line
  2426. push str_equ
  2427. push edx
  2428. call strcmp
  2429. add esp, 8
  2430. pop edx
  2431. ;; Fail if we are not
  2432. cmp eax, 0
  2433. jne process_equ_line_ret_false
  2434. ;; Call trimstr
  2435. push edx
  2436. push edx
  2437. call trimstr
  2438. add esp, 4
  2439. pop edx
  2440. ;; Call decode_number_or_symbol
  2441. push 0
  2442. mov ecx, esp
  2443. push 0
  2444. push ecx
  2445. push edx
  2446. call decode_number_or_symbol
  2447. add esp, 12
  2448. ;; Panic if it did not work
  2449. cmp eax, 0
  2450. je platform_panic
  2451. ;; Create a symbol if it did work
  2452. pop edx
  2453. mov eax, [esp+4]
  2454. push 0xffffffff
  2455. push edx
  2456. push eax
  2457. call add_symbol_wrapper
  2458. add esp, 12
  2459. ;; Return true
  2460. mov eax, 1
  2461. ret
  2462. process_equ_line_ret_false:
  2463. mov eax, 0
  2464. ret
  2465. global process_line
  2466. process_line:
  2467. ;; Find first space
  2468. mov eax, [esp+4]
  2469. push SPACE
  2470. push eax
  2471. call find_char
  2472. add esp, 8
  2473. ;; Select on whether we found it or not
  2474. cmp eax, 0xffffffff
  2475. je process_line_without_space
  2476. jmp process_line_with_space
  2477. process_line_with_space:
  2478. ;; Substitute the space with a terminator; leave opcode in edx and
  2479. ;; data in eax
  2480. mov edx, [esp+4]
  2481. add eax, edx
  2482. mov BYTE [eax], 0
  2483. add eax, 1
  2484. jmp process_line_process
  2485. process_line_without_space:
  2486. ;; Leave opcode in edx and set data (in eax) to an empty string
  2487. mov edx, [esp+4]
  2488. mov eax, str_empty
  2489. jmp process_line_process
  2490. process_line_process:
  2491. ;; Call all line processing functions
  2492. push eax
  2493. push edx
  2494. push eax
  2495. push edx
  2496. call process_directive_line
  2497. add esp, 8
  2498. cmp eax, 0
  2499. pop edx
  2500. pop eax
  2501. jne process_line_end
  2502. push eax
  2503. push edx
  2504. push eax
  2505. push edx
  2506. call process_bss_line
  2507. add esp, 8
  2508. cmp eax, 0
  2509. pop edx
  2510. pop eax
  2511. jne process_line_end
  2512. push eax
  2513. push edx
  2514. push eax
  2515. push edx
  2516. call process_text_line
  2517. add esp, 8
  2518. cmp eax, 0
  2519. pop edx
  2520. pop eax
  2521. jne process_line_end
  2522. push eax
  2523. push edx
  2524. push eax
  2525. push edx
  2526. call process_data_line
  2527. add esp, 8
  2528. cmp eax, 0
  2529. pop edx
  2530. pop eax
  2531. jne process_line_end
  2532. push eax
  2533. push edx
  2534. push eax
  2535. push edx
  2536. call process_equ_line
  2537. add esp, 8
  2538. cmp eax, 0
  2539. pop edx
  2540. pop eax
  2541. jne process_line_end
  2542. ;; Nothing matched, panic
  2543. call platform_panic
  2544. process_line_end:
  2545. ret
  2546. global init_assembler
  2547. init_assembler:
  2548. ;; Allocate input buffer
  2549. push INPUT_BUF_LEN
  2550. call platform_allocate
  2551. add esp, 4
  2552. mov ecx, input_buf_ptr
  2553. mov [ecx], eax
  2554. ret
  2555. global assemble
  2556. assemble:
  2557. push ebp
  2558. mov ebp, esp
  2559. push esi
  2560. push edi
  2561. push ebx
  2562. ;; Set fd for emit
  2563. mov eax, emit_fd
  2564. mov ecx, [ebp+12]
  2565. mov [eax], ecx
  2566. ;; Reset stage
  2567. mov eax, stage
  2568. mov DWORD [eax], 0
  2569. assemble_stage_loop:
  2570. ;; Check for termination
  2571. mov eax, stage
  2572. cmp DWORD [eax], 2
  2573. je assemble_end
  2574. ;; Call platform_reset_file
  2575. mov eax, [ebp+8]
  2576. push eax
  2577. call platform_reset_file
  2578. add esp, 4
  2579. ;; Reset line number (in esi) and current_loc
  2580. mov esi, 0
  2581. mov eax, current_loc
  2582. mov ecx, [ebp+16]
  2583. mov [eax], ecx
  2584. assemble_parse_loop:
  2585. ;; Call readline and store in ebx if we found the EOF
  2586. push INPUT_BUF_LEN
  2587. mov eax, input_buf_ptr
  2588. mov eax, [eax]
  2589. push eax
  2590. mov eax, [ebp+8]
  2591. push eax
  2592. call readline
  2593. add esp, 12
  2594. mov ebx, eax
  2595. ;; Log the line
  2596. ;; push str_decoding_line
  2597. ;; push 2
  2598. ;; call platform_log
  2599. ;; add esp, 8
  2600. ;; mov eax, input_buf_ptr
  2601. ;; mov eax, [eax]
  2602. ;; push eax
  2603. ;; push 2
  2604. ;; call platform_log
  2605. ;; add esp, 8
  2606. ;; push str_newline
  2607. ;; push 2
  2608. ;; call platform_log
  2609. ;; add esp, 8
  2610. ;; Find the first semicolon
  2611. push SEMICOLON
  2612. mov eax, input_buf_ptr
  2613. mov eax, [eax]
  2614. push eax
  2615. call find_char
  2616. add esp, 8
  2617. ;; If found, substitute it with a terminator
  2618. cmp eax, 0xffffffff
  2619. je assemble_parse_trim
  2620. mov ecx, input_buf_ptr
  2621. add eax, [ecx]
  2622. mov BYTE [eax], 0
  2623. assemble_parse_trim:
  2624. ;; Call trimstr
  2625. mov eax, input_buf_ptr
  2626. mov eax, [eax]
  2627. push eax
  2628. call trimstr
  2629. add esp, 4
  2630. ;; Compute line length and store it in edi
  2631. mov eax, input_buf_ptr
  2632. mov eax, [eax]
  2633. push eax
  2634. call strlen
  2635. add esp, 4
  2636. mov edi, eax
  2637. ;; If the line is not empty, pass to parsing it
  2638. cmp edi, 0
  2639. jne assemble_parse_detect_symbol
  2640. ;; If it is empty and we have finished, break
  2641. cmp ebx, 0
  2642. jne assemble_break_parse_loop
  2643. ;; If it is empty and we have not finished, continue
  2644. jmp assemble_continue_parse_loop
  2645. assemble_parse_detect_symbol:
  2646. ;; Detect if this line is a symbol declaration
  2647. mov eax, input_buf_ptr
  2648. mov eax, [eax]
  2649. add eax, edi
  2650. sub eax, 1
  2651. cmp BYTE [eax], COLON
  2652. jne assemble_parse_process
  2653. ;; Substitute the colon with a terminator
  2654. mov BYTE [eax], 0
  2655. ;; Call add_symbol_wrapper
  2656. push 0xffffffff
  2657. mov edx, current_loc
  2658. mov eax, [edx]
  2659. push eax
  2660. mov eax, input_buf_ptr
  2661. mov eax, [eax]
  2662. push eax
  2663. call add_symbol_wrapper
  2664. add esp, 12
  2665. jmp assemble_continue_parse_loop
  2666. assemble_parse_process:
  2667. ;; Call process_line
  2668. mov eax, input_buf_ptr
  2669. mov eax, [eax]
  2670. push eax
  2671. call process_line
  2672. add esp, 4
  2673. jmp assemble_continue_parse_loop
  2674. assemble_continue_parse_loop:
  2675. ;; Increment line number and restart parse loop
  2676. add esi, 1
  2677. jmp assemble_parse_loop
  2678. assemble_break_parse_loop:
  2679. ;; Increment stage
  2680. mov eax, stage
  2681. add DWORD [eax], 1
  2682. jmp assemble_stage_loop
  2683. assemble_end:
  2684. ;; Print processed line number
  2685. push str_ass_finished1
  2686. push 2
  2687. call platform_log
  2688. add esp, 8
  2689. push esi
  2690. call itoa
  2691. add esp, 4
  2692. push eax
  2693. push 2
  2694. call platform_log
  2695. add esp, 8
  2696. push str_ass_finished2
  2697. push 2
  2698. call platform_log
  2699. add esp, 8
  2700. ;; Print symbol number
  2701. push str_symb_num1
  2702. push 2
  2703. call platform_log
  2704. add esp, 8
  2705. mov ecx, symbol_num
  2706. mov eax, [ecx]
  2707. push eax
  2708. call itoa
  2709. add esp, 4
  2710. push eax
  2711. push 2
  2712. call platform_log
  2713. add esp, 8
  2714. push str_symb_num2
  2715. push 2
  2716. call platform_log
  2717. add esp, 8
  2718. pop ebx
  2719. pop edi
  2720. pop esi
  2721. pop ebp
  2722. ret