Welcome, Guest. Please login or register.


Author Topic: Assembly programozás (Read 254502 times)

Offline Zozosoft

  • Global Moderator
  • EP addict
  • *
  • Posts: 14723
  • Country: hu
    • http://enterprise.iko.hu/
Re: Assembly programozás
« Reply #360 on: 2012.December.08. 20:00:37 »
Az ilyesmi az tényleg valóban igen számítás igényes, kell egy osztó rutin, és sorban osztogatni, pl 16 bitesnél elsőként 10000-el, a kapott értéket kiírni, aztán az érték x 10000-t levonni az eredetiből, ismételni 1000-el, stb.
32 bitesnél ugyan ez, csak sokkal több értékkel.

Általában ezért el is kerülik az ilyet, és eleve BCD-ben tárolják a nagyobb értékeket, az IS-BASIC is ezt teszi 32768 felett.

EXDOS-ban ahol pl a fájlméreteknél nem lehet elkerülni a dolgot, az említett osztogatós módon csinálja, itt a kérdéses rész:
Code: ZiLOG Z80 Assembler
  1.         ;DE-ben megadott 16 bites érték konvertálása a szövegpufferbe
  2.         ;a bevezető nullákat levágja
  3.         ;HL számpufferre mutat
  4.  
  5. lf1f4:  XOR     A
  6.         LD      (HL),A          ;számpuffer
  7.         DEC     HL              ;felső 16 bitje
  8.         LD      (HL),A          ;nullázva
  9.         DEC     HL
  10.         LD      (HL),D          ;érték
  11.         DEC     HL              ;letárolva
  12.         LD      (HL),E          ;a számpufferbe
  13.         EX      DE,HL           ;DE mutat a számpufferre
  14.  
  15.  
  16.         ;számpufferben megadott 32 bites érték konvertálása a szövegpufferbe
  17.         ;a bevezető nullákat levágja
  18.         ;DE számpufferre mutat
  19.         ;A=bevezető karakter kódja, 00H esetén nem ír ki semmit
  20.  
  21. lf1fd:  EXX    
  22.         LD      E,A             ;0, jelzi, hogy nulla eredmény esetén
  23.                                 ;még bevezető nulláról van szó
  24.         LD      D,30H           ;"0"
  25.         EXX    
  26.         LD      HL,lf233        ;számkonstansok táblázatára mutat
  27. lf205:  LD      A,(HL)         
  28.         DEC     A               ;=1? vagyis a táblázat legkisebb eleme?
  29.         JR      NZ,LF20C        ;ugrás ha nem
  30.         EXX                     ;ha igen
  31.         LD      E,D             ;E="0" mindenképpen kiírja a nulla eredményt is
  32.         EXX                      
  33.  
  34.         ;32 bites osztás (DE)/(HL)
  35.         ;C=az osztás eredménye, (DE)=maradék
  36.      
  37. lf20c:  XOR     A               ;C flag törlése
  38.         LD      C,A             ;C=0
  39.        
  40.         ;az osztást kivonással hajtja végre, amíg negatív nem lesz
  41.  
  42. lf20e:  PUSH    HL
  43.         PUSH    DE
  44.         LD      B,04H           ;4 bájton kell elvégezni a műveletet
  45. lf212:  LD      A,(DE)          ;csökkentendő bájt
  46.         SBC     A,(HL)          ;kivonás
  47.         LD      (DE),A          ;letárolás
  48.         INC     HL              ;mutatók
  49.         INC     DE              ;növelése
  50.         DJNZ    LF212           ;művelet elvégzése a többi bájton
  51.         POP     DE              ;eredeti mutatók
  52.         POP     HL              ;vissza
  53.         INC     C               ;eredmény növelése
  54.         JR      NC,LF20E        ;újabb kivonás, ha még nem negatív az eredmény
  55.         CALL    LF254           ;(DE)+(HL), az utolsó kivonás visszacsinálása
  56.                                 ;így (DE)-ben a maradék lesz
  57.                                 ;HL=HL+4, a következő konstansra mutat
  58.  
  59.         LD      A,C             ;eredmény A-ba
  60.         EXX    
  61.         DEC     A               ;eredmény csökkentése eggyel
  62.                                 ;a visszacsinált kivonás miatt
  63.         JR      Z,LF229         ; (+03h)
  64.         ADD     A,D             ;A+"0", vagyis az eredmény ASCII
  65.                                 ;karakterré konvertálása
  66.         LD      E,D             ;E="0", vagyis ha volt már egy értékes
  67.                                 ;karakter, innentől kezdve kiírja a nulla
  68.                                 ;karaktereket is, a szám elején lévő
  69.                                 ;nullákat levágja
  70.         DB      2EH             ;töltelék bájt az OR E átugrásához
  71. LF229:  OR      E               ;nullás eredmény esetén megvizsgálja, hogy
  72.                                 ;bevezető nulláról, vagy már szám közben
  73.                                 ;lévő nulláról van szó
  74.         CALL    NZ,LF040        ;ha nem bevezető nulla, akkor karakter írása szövegpufferbe
  75.         EXX    
  76.         LD      A,(HL)          ;táblázat következő eleme
  77.         INC     A               ;=255? azaz lista vége?
  78.         JR      NZ,LF205        ;folytatás a következővel, ha még nincs vége
  79.         RET    
  80.  
  81. lf233:  DB      80H,96H,98H,00H ;00989680H=10000000
  82.         DB      40H,42H,0FH,00H ;000F4240H= 1000000
  83.         DB     0A0H,86H,01H,00H ;000186A0H=  100000
  84.         DB      10H,27H,00H,00H ;00002710H=   10000
  85.         DB     0E8H,03H,00H,00H ;000003E8H=    1000
  86.         DB      64H,00H,00H,00H ;00000064H=     100
  87.         DB      0AH,00H,00H,00H ;0000000AH=      10
  88.         DB      01H,00H,00H,00H ;00000001H=       1
  89.         DB      0FFH            ;lista vége
  90.  
  91.         ;32 bites összeadás, (DE)=(DE)+(HL)
  92.         ;HL=HL+4
  93.  
  94. lf254:  PUSH    DE
  95.         LD      B,04H           ;4 bájton kell elvégezni a műveletet
  96.         OR      A               ;C flag törlése
  97. lf258:  LD      A,(DE)          ;növelendő bájt
  98.         ADC     A,(HL)          ;hozzáadás
  99.         LD      (DE),A          ;letárolás
  100.         INC     HL              ;mutatók
  101.         INC     DE              ;növelése
  102.         DJNZ    LF258           ;művelet elvégzése a többi bájton
  103.         POP     DE
  104.         RET    

Offline Tuby128

  • EP addict
  • *
  • Posts: 1448
  • Country: hu
Re: Assembly programozás
« Reply #361 on: 2012.December.08. 20:11:21 »
Nagyon-nagyon köszönöm a válszt!
 Az osztás a Z80 esetében nagyon sok időt vesz igénybe. Gondolom legfőképpen ezért olyan időigényes. Továbbá, mivel a regiszterek 8 bitesek, fel kell osztani az egészet részekre.
 Valami hasonlóra gondoltam én is, mint ami a kódban van.
 Egy dolog: Az osztás után nem kell visszaszorozni és kivonni, mert egy tisztességes osztó rutin után megkapjuk a maradékot is.

 Rájöttem, hogy a visszafelé történő konverzió is nagyon fontos! Ha felhasználó megadja BASIC-ben, hogy
PRINT 47500+23456 akkor vajon mit csinál ezekkel a tagokkal? BCD-ben számol vagy átalakítja kiszámolja és visszaalakítja?
 

Offline IstvanV

  • EP addict
  • *
  • Posts: 4822
Re: Assembly programozás
« Reply #362 on: 2012.December.08. 20:28:20 »
Quote from: Zozosoft
Az ilyesmi az tényleg valóban igen számítás igényes, kell egy osztó rutin, és sorban osztogatni, pl 16 bitesnél elsőként 10000-el, a kapott értéket kiírni, aztán az érték x 10000-t levonni az eredetiből, ismételni 1000-el, stb.
32 bitesnél ugyan ez, csak sokkal több értékkel.
Szorzás valójában nem kell, mert az osztó rutin a maradékot is kiszámítja. Ráadásul használható egyszerű ciklusban kivonás az osztás megvalósítására, mert az eredmény nem lehet nagyobb, mint 9.

Az ASCII->bináris szám konverzió könnyű, mert csak 10-el szorozni és a következő számjegyet hozzáadni kell ciklusban. A konstans 10-el szorzás pedig viszonylag egyszerű és gyors művelet.
« Last Edit: 2012.December.08. 20:32:59 by IstvanV »

Offline Tuby128

  • EP addict
  • *
  • Posts: 1448
  • Country: hu
Re: Assembly programozás
« Reply #363 on: 2012.December.08. 21:25:41 »
BCD -> BIN-t akartál írni ugye? Mert az ASCII az más, ott az "12"-nek 31 32 a kódja. Bár a felső nibble leharapásával igaz megkapjuk a BCD kódot.

 Ez 10-zel való szorzósdi nem a legjobb ötlet, szorzás híjján változó, hogy hányszor kell összeadnunk, a legjobb eset a csupa nulla lesz a legrosszabb meg a sok kilences. 16-bit esetén is azért kell számolni keményen.

Offline geco

  • EP addict
  • *
  • Posts: 7082
  • Country: hu
    • Támogató Támogató
Re: Assembly programozás
« Reply #364 on: 2013.February.18. 15:55:02 »
Hogyan kerülhetném el két LPT közötti váltás miatti kép ugrást?
Csak a 82h portot írom, és így csak akkor vált a másik LPT-re, ha az elsőn végigfutott, és mégis ugrik egyet a kép, a két LPT teljesen más felépítésű, az egyik elején van státus sor is, és 200 soros képet definiál 1 LPB-ben, a másik elején nincs státusz sor, és 200 soros képet definiál 25 LPB-ben.

Offline IstvanV

  • EP addict
  • *
  • Posts: 4822
Re: Assembly programozás
« Reply #365 on: 2013.February.18. 16:00:20 »
A két LPT-ben azonosnak kell lennie a VSYNC és RELOAD közötti távolságnak.

Csak érdekességként itt egy megoldás a HL-ben található LPT cím bállítására, ami rövid, és minimális az idő a 82h és 83h port írása között:

Code: [Select]
        ld      a, 1ch
.l1:    add     hl, hl
        rla
        jr      nc, .l1
        ld      c, 82h
        out     (c), h
        out     (83h), a
« Last Edit: 2013.February.18. 16:05:28 by IstvanV »

Offline geco

  • EP addict
  • *
  • Posts: 7082
  • Country: hu
    • Támogató Támogató
Re: Assembly programozás
« Reply #366 on: 2013.February.18. 16:04:29 »
Quote from: IstvanV
A két LPT-ben azonosnak kell lennie a VSYNC és RELOAD közötti távolságnak.
Köszönöm szépen :) Ez mindent megmagyaráz :D az utolsó sor a vsyncben, ahol a RELOAD bit van, eltér, pont Státuss sorbeli különbség miatt :D, de akkor kiiktatom a státusz sort mikor a program elindul, és visszaállítom RELOAD-os sor értékét. Köszi szépen mégeccer :)

Offline geco

  • EP addict
  • *
  • Posts: 7082
  • Country: hu
    • Támogató Támogató
Re: Assembly programozás
« Reply #367 on: 2013.February.18. 16:27:19 »
Nagyon jóóó :smt041 :smt041 :smt041 :smt041

Offline lgb

  • EP addict
  • *
  • Posts: 3563
  • Country: hu
  • æðsta yfirmaður
    • http://lgb.hu/
Re: Assembly programozás
« Reply #368 on: 2013.March.20. 11:05:33 »
Lenne par EXOS-al kapcsolatos kerdesem ... Van egy olyan problemam, hogy egy 5-os fejlecu (sajat fejlesztesu) programnal nekem meg kell valtoztatni a B0 memory mapping I/O register erteket, tekintve, hogy 0x100 alatti dolgokra szuksegem van, es ezen nem tudok valtoztatni. Eloszor is kerdeses, hogy mi az a minimalis dolog ott, aminek ott kell lennie, hogy interrupt-ok letiltasa nelkul ne fekudjon meg a rendszer. Masreszt: mi tortenik, ha kozben valaki megnyomja a RESET gombot? Az EXOS warm reset vectort (0xBFF8) modosithatom, amde nem teljesen vilagos, hogy az ott megadott cim konkretan melyik EP szegmensben ertendo, akkor EXOS visszallitja az eredeti belapozott szegmenseket, es ugy kell nekem ehhez viszonyitani? Tovabba: problema, hogy kene nekem egy kis minimalis terulet, ahol dolgozhatok, es ez VRAM kell hogy legyen. Emiatt viszont kene egy plusz szegmens, amit gaznak erzek, mert amugy kell par masik is. Van az az osztott szegmens dolog, ahol van az EXOS boundary stb, mi van ha en siman a boundary-t figyelembe veve onhatalmulag elkezdem hasznalni, vagy ilyet nem "illik"? Ha kell nekem vmi custom LPT, akkor nekem kotelezo ehhez uj vram szegmenst foglalnom (a szokasos "foglalj szegmenseket amig nem kapsz a vram-bol" algoritmussal), vagy megoldhato, hogy exos altal is hasznalt hasonlo celu teruletre "belepasszirozom" szep csunyan? Maguk a pixel adatok mashonnan jonnek (persze nyilvan szinten vram) szoval az itt nem kerdes.

Nem teljesen biztos, hogy ez "assembly programozas" temaba illik-e vagy kulon EXOS topic lenne, de assemblyben irom legalabb :)

Koszi!

Offline Zozosoft

  • Global Moderator
  • EP addict
  • *
  • Posts: 14723
  • Country: hu
    • http://enterprise.iko.hu/
Re: Assembly programozás
« Reply #369 on: 2013.March.20. 11:41:06 »
Az EXOS a 30h-5Bh területet használja, tehát a 00h-2Fh, 5Ch-FFh a tiéd lehet, ha ez elég, akkor nem is kell piszkálnod a nullás lapot. Ha nem elég, akkor tiltanod kell a megszakításokat.
Resetnél az USR_P0-ba bejegyzett szegmenst lapozza a nullás lapra, célszerű ha ide mutat az újraindítási cím.
Az önhatalmú figyelembevétellel az a baj, hogy ha nem foglaltad le a közös szegmenst, akkor az EXOS nem fogja tudni, hogy te ott ténykedsz, és belemászik a szabálytalanul használt területedbe.
Az EXOS határ az csak egy nyilvántartási érték, amit egyrészt közöl veled amikor osztott szegmenst kapsz, hogy éppen akkor mennyi a szabad terület, másrészt miután beállítottad, hogy az osztott szegmensben mennyi hely kell, a további EXOS memóriaigényeknél ezzel hasonlítja össze, hogy tud-e még terjeszkedni.
Pl, 2000H az EXOS határ, neked 1000H kell, mikor megkapod az osztott szegmenst sikeres az ellenőrzésed, mert van elég hely. Beállítod a felhasználói határt, innentől tudja az EXOS, hogy 1000H-ig terjeszkedhet még.

Az LPT és a karakterkészlet (ha nem kell karakteres mód) helyét használhatod videómemóriának pl LPT-hez, csak ki kell keresni a helyüket, hogy 2.0 és 2.1+ verziókkal is működjön.
Az LPT végét viszont nem érdemes felhasználni, mert pl a német bővítés folyamatosan kijavítja a szinkron részt.

Offline IstvanV

  • EP addict
  • *
  • Posts: 4822
Re: Assembly programozás
« Reply #370 on: 2013.March.20. 12:38:18 »
Felhasználható még az EXOS verem nagy része is (AC00h-AFFFh), a megmaradt több mint 500 byte hely elég az EXOS megszakításkezelőjéhez és egyszerű csatorna műveletekhez (pl. file betöltés).

Offline lgb

  • EP addict
  • *
  • Posts: 3563
  • Country: hu
  • æðsta yfirmaður
    • http://lgb.hu/
Re: Assembly programozás
« Reply #371 on: 2013.March.21. 15:20:10 »
Koszi az infokat! Most eppen felre teve a nullas lap kerdeset, a kovetkezo a problemam: ha lehet elsore nem akarom megvaltani a vilagot, sajat LPT stb. Megoldhato-e ertelmesen, hogy EXOS-tol szepen kerek adott kello videomodot nekem (exos valtozok beallitasa, majd megnyitom a display channelt, aztan johet a 11-es spec 1-es funkcio, hogy mutassa is meg, ezzel nincs is gondom: mukodik), _AMDE_ azzal a csavarral h pl pixel modban en szeretnem megmondani hogy honnan jojjenek az adatok, magyaran a megfelelo LPB LD1 erteket szeretnem modositani (az nekem tok oke, hogy az LPT-t - a fenti LD1-en kivul - az EXOS-ra bizom). Ezt "kitalalos" alapon kicsit nehez, meg bezavarhat hogy most EXOS milyen verzio stb. Van otletetek, hogy lehetne szepen megcsinalni ezt? Kicsit nagy az overhead, hogy most csak 2 byte miatt (LD1) csinaljak sajat LPT-t, stb stb. Vagy ezt nem fogom tudni kikerulni? Mert a gondom az, hogy ahol maguk a pixel adatok vannak annak a helye kotott, amde ott LPT pl nem is ferne el (ezert is akartam elozo postomban valamire "ralsozni" az LPT-t egy masik szegmensbe).

Offline geco

  • EP addict
  • *
  • Posts: 7082
  • Country: hu
    • Támogató Támogató
Re: Assembly programozás
« Reply #372 on: 2013.March.21. 16:33:14 »
Quote from: lgb
Koszi az infokat! Most eppen felre teve a nullas lap kerdeset, a kovetkezo a problemam: ha lehet elsore nem akarom megvaltani a vilagot, sajat LPT stb. Megoldhato-e ertelmesen, hogy EXOS-tol szepen kerek adott kello videomodot nekem (exos valtozok beallitasa, majd megnyitom a display channelt, aztan johet a 11-es spec 1-es funkcio, hogy mutassa is meg, ezzel nincs is gondom: mukodik), _AMDE_ azzal a csavarral h pl pixel modban en szeretnem megmondani hogy honnan jojjenek az adatok, magyaran a megfelelo LPB LD1 erteket szeretnem modositani (az nekem tok oke, hogy az LPT-t - a fenti LD1-en kivul - az EXOS-ra bizom). Ezt "kitalalos" alapon kicsit nehez, meg bezavarhat hogy most EXOS milyen verzio stb. Van otletetek, hogy lehetne szepen megcsinalni ezt? Kicsit nagy az overhead, hogy most csak 2 byte miatt (LD1) csinaljak sajat LPT-t, stb stb. Vagy ezt nem fogom tudni kikerulni? Mert a gondom az, hogy ahol maguk a pixel adatok vannak annak a helye kotott, amde ott LPT pl nem is ferne el (ezert is akartam elozo postomban valamire "ralsozni" az LPT-t egy masik szegmensbe).
Módosítsd az LD1 értékeit, 0bff4h megadja az LPT címét, és ez egy fix EXOS változó, minden EXOS-ban ugyanott van.

Offline Zozosoft

  • Global Moderator
  • EP addict
  • *
  • Posts: 14723
  • Country: hu
    • http://enterprise.iko.hu/
Re: Assembly programozás
« Reply #373 on: 2013.March.21. 17:48:03 »
Pontosan mit is szeretnél (Milyen méretű, felbontású kép?)

Offline Z80System

  • EP addict
  • *
  • Posts: 3848
  • Country: hu
Re: Assembly programozás
« Reply #374 on: 2013.March.23. 20:26:57 »
Gondolkodok itt fejlesztgetesekben ...

Es az van, hogy az elmult evtizedekben baromira hozzaszoktam a magasabb szintu progrmnyelvekhez (C, C++, C#, java es az osszes tobbi),
es mikor leulok az assembler ele, baromira frusztral, hogy 2 napig szenvedek, es odaig jutottam, hogy "szuper, sikerult osszehasonlitani 2 sztringet" ...

szoval probalnek minnel magasabb szintu programozasi lehetosegeket talalni EP- re (akar oly modon is, hogy elbukom az EP fejlesztest, es valami kereszt fejlesztesi modszert hasznalok, ami ugye az ep128emu- nak hala eleg gyors tud lenni),

masreszrol szeretnem megtartani a kozvetlen z80 assembly kompaktsagat, kis meretet, relokalhatosagat, sebesseget, nem beszelve az EP fejlesztes elmenyerol. tehat hogy tenyleg EP- n lett fejleszteve, nem kereszt fejlesztessel.

kiprobaltam az SDCC- t, ossze is hoztam hogy adjon nekem egy EP- n futathato binarist a vege, C- ben lehet fejleszteni, ami tokeletesen eleg, es a legalapvetobb assembly szenvedestol megszabadit, viszont a forditott kod az SDCC- vel szerintem marha nagy lesz, mikor float- okat szamolok, akkor pedig iszonyatosan nagy ... nem tusom miert haragszik erre, de a float- os szamitasok mintha alkalmazasrol alkalmazasra nonenek ... tehat nem az hogy 1X hozzarakja a float rutinokat, hanem barhanyszor hivom oket a kod no mint a gomba ...

szoval nem tetszett (megha a csillagos effekt framework kodjait abban is irtam).

most azon gondolkodok, hogy ossze kene rakni ASSEMBLER MACRO- kbol olyan library- t, ami legalabb az alapveto valtozohasznalatot, fuggveny parameteratadast, neadjisten vezerlesi szerkezeteket tartalmazna, es regiszterfuggetlenne tenne.

ez is nyilvan nagyobb meretu volna mint az igazi assembly, de sztm korantsem akkora mint egy rendes C - bol forditott kod, vagy legalabbis az SDCC- vel forditott.

tehat arra gondolok, hogy adat strukturakat, es stack frame strukturakat felvennek define- okkal, mezo offsetekkel, mezo meretekkel, es ezekel az ofsetekkel lehetne makrokat hivni, ami valami a makroban rogzitett regiszterekben tarolt cimekhez kepesti offsetkent ertelmezve, kepes lenne tetszoleges szamu valtozon elvegezni az alap muveleteket, add, sub, inc, cmp, 

es mivel ezek a valtozok stack- en felvett memoriaban lennenek, nem regiszterekben, ezert a moder nyelvek konnyedsegevel lehetne programozni. persze kicsit (sokkal) tobb lenne az irogatas, de nem kene azzal bibelodni, hogy hany regiszered van, es azok kozul melyikben eppen mi, hanem a regisztereket stack memoriavaltozok helyettesitenek, mint a C- ben.

termeszetesen nem a putpixel ciklusmagokban kene ezeket alkalmazni, de ugy a programok teruleteinek masik 95%- an sokkal konnyebb lenne haladni, nem igenyelne egyeb forditot, EP assemblerekkel lehetne dolgozni, es a kod sem none meg iszonyuan.

elkezdtem egy ilyen framework- ben gondolkodni, de egyenlore eleg nagy munkanak latom... es arra gondoltam valszeg nem nekem jut eszembe ez eloszor... ez meg ugye nem C, de mar nem is direkt assembly lenne... egy MACRO meta nyelv tulajdonkeppen, z80 assembly- vel leirva ...

szoval nem halott mar valaki ilyenrol ? lehet hogy van mar 50 kulonbozo megvalositas, csak en nem tudok rola ...
Z80 System