mirror of
https://github.com/thrust26/6502-QR-code-generator.git
synced 2024-12-27 19:29:35 +00:00
added option to generate RS polynomial on-the-fly
This commit is contained in:
parent
731550443b
commit
d150cbc5af
159
QRCodeGen.inc
159
QRCodeGen.inc
@ -78,49 +78,6 @@ QR_TOTAL = QR_MAX_DATA + QR_DEGREE ; 44
|
|||||||
; The following code has been partially converted from the C code of the
|
; The following code has been partially converted from the C code of the
|
||||||
; QR code generator found at https://github.com/nayuki/QR-Code-generator
|
; QR code generator found at https://github.com/nayuki/QR-Code-generator
|
||||||
|
|
||||||
;-----------------------------------------------------------
|
|
||||||
MAC _RS_REMAINDER
|
|
||||||
;-----------------------------------------------------------
|
|
||||||
.i = tmpVars+2
|
|
||||||
.factor = tmpVars+3
|
|
||||||
|
|
||||||
; memset(result, 0, 16); // done in START_TEXT
|
|
||||||
; for (int i = dataLen-1; i >= 0; i--) { // Polynomial division
|
|
||||||
ldx #QR_MAX_DATA-1
|
|
||||||
.loopI
|
|
||||||
stx .i
|
|
||||||
; uint8_t factor = data[i] ^ result[degree - 1];
|
|
||||||
lda msgData,x
|
|
||||||
eor remainder + QR_DEGREE - 1
|
|
||||||
sta .factor
|
|
||||||
; memmove(&result[1], &result[0], (size_t)(16 - 1) * sizeof(result[0]));
|
|
||||||
ldx #QR_DEGREE-1
|
|
||||||
.loopMove
|
|
||||||
lda remainder-1,x
|
|
||||||
sta remainder,x
|
|
||||||
dex
|
|
||||||
bne .loopMove
|
|
||||||
; result[0] = 0;
|
|
||||||
lda #0
|
|
||||||
sta remainder
|
|
||||||
; for (int j = 16-1; j >= 0; j--)
|
|
||||||
ldx #QR_DEGREE-1
|
|
||||||
.loopJ
|
|
||||||
; result[j] ^= reedSolomonMultiply(generator[j], factor);
|
|
||||||
lda Generator,x
|
|
||||||
ldy .factor
|
|
||||||
_RS_MULT
|
|
||||||
eor remainder,x
|
|
||||||
sta remainder,x
|
|
||||||
; }
|
|
||||||
dex
|
|
||||||
bpl .loopJ
|
|
||||||
; }
|
|
||||||
ldx .i
|
|
||||||
dex
|
|
||||||
bpl .loopI
|
|
||||||
ENDM
|
|
||||||
|
|
||||||
;-----------------------------------------------------------
|
;-----------------------------------------------------------
|
||||||
; Returns the product of the two given field elements modulo GF(2^8/0x11D).
|
; Returns the product of the two given field elements modulo GF(2^8/0x11D).
|
||||||
; All inputs are valid.
|
; All inputs are valid.
|
||||||
@ -154,6 +111,114 @@ QR_TOTAL = QR_MAX_DATA + QR_DEGREE ; 44
|
|||||||
bpl .loopI
|
bpl .loopI
|
||||||
ENDM
|
ENDM
|
||||||
|
|
||||||
|
IF QR_GENERATE
|
||||||
|
; Computes a Reed-Solomon ECC generator polynomial for degree 16, storing in result[0 : 16-1].
|
||||||
|
; This is implemented as a lookup table too (Generator)
|
||||||
|
;-----------------------------------------------------------
|
||||||
|
MAC _RS_DIVISOR
|
||||||
|
;-----------------------------------------------------------
|
||||||
|
; E.g. g(x)=(x+1)(x+?)(x+?^2)(x+?^3)...(x+?^15)
|
||||||
|
; = x^16+3Bx^15+0Dx^14+68x^13+BDx^12+44x^11+d1x^10+1e^x9+08x^8
|
||||||
|
; +A3x^7+41x^6+29x^5+E5x^4+62x^3+32x^2+24x+3B
|
||||||
|
.root = tmpVars+2
|
||||||
|
.i = tmpVars+3
|
||||||
|
|
||||||
|
; memset(qrGenerator, 1, 16);
|
||||||
|
ldx #QR_DEGREE-1
|
||||||
|
stx .i
|
||||||
|
ldy #0
|
||||||
|
.loopClear
|
||||||
|
sty qrGenerator,x
|
||||||
|
dex
|
||||||
|
bne .loopClear
|
||||||
|
; qrGenerator[0] = 1; // Start off with the monomial x^0
|
||||||
|
iny
|
||||||
|
sty qrGenerator
|
||||||
|
; uint8_t root = 1;
|
||||||
|
sty .root
|
||||||
|
; for (int i = 0; i < degree; i++) {
|
||||||
|
.loopI
|
||||||
|
; // Multiply the current product by (x - r^i)
|
||||||
|
; for (int j = degree-1; j >= 0; j--) {
|
||||||
|
ldx #QR_DEGREE-1
|
||||||
|
.loopJ
|
||||||
|
; qrGenerator[j] = reedSolomonMultiply(qrGenerator[j], root);
|
||||||
|
lda qrGenerator,x
|
||||||
|
ldy .root
|
||||||
|
jsr RSMult
|
||||||
|
; if (j)
|
||||||
|
dex
|
||||||
|
bmi .skipEor
|
||||||
|
; qrGenerator[j] ^= qrGenerator[j - 1];
|
||||||
|
eor qrGenerator,x
|
||||||
|
.skipEor
|
||||||
|
sta qrGenerator+1,x
|
||||||
|
txa
|
||||||
|
bpl .loopJ
|
||||||
|
; root = reedSolomonMultiply(root, 0x02);
|
||||||
|
lda .root
|
||||||
|
ldy #$02
|
||||||
|
jsr RSMult
|
||||||
|
sta .root
|
||||||
|
dec .i
|
||||||
|
bpl .loopI
|
||||||
|
ENDM
|
||||||
|
|
||||||
|
;-----------------------------------------------------------
|
||||||
|
RSMult SUBROUTINE
|
||||||
|
_RS_MULT
|
||||||
|
rts
|
||||||
|
;-----------------------------------------------------------
|
||||||
|
ENDIF ; /QR_GENERATE
|
||||||
|
|
||||||
|
;-----------------------------------------------------------
|
||||||
|
MAC _RS_REMAINDER
|
||||||
|
;-----------------------------------------------------------
|
||||||
|
.i = tmpVars+2
|
||||||
|
.factor = tmpVars+3
|
||||||
|
|
||||||
|
; memset(result, 0, 16); // done in START_TEXT
|
||||||
|
; for (int i = dataLen-1; i >= 0; i--) { // Polynomial division
|
||||||
|
ldx #QR_MAX_DATA-1
|
||||||
|
.loopI
|
||||||
|
stx .i
|
||||||
|
; uint8_t factor = data[i] ^ result[degree - 1];
|
||||||
|
lda msgData,x
|
||||||
|
eor remainder + QR_DEGREE - 1
|
||||||
|
sta .factor
|
||||||
|
; memmove(&result[1], &result[0], (size_t)(16 - 1) * sizeof(result[0]));
|
||||||
|
ldx #QR_DEGREE-1
|
||||||
|
.loopMove
|
||||||
|
lda remainder-1,x
|
||||||
|
sta remainder,x
|
||||||
|
dex
|
||||||
|
bne .loopMove
|
||||||
|
; result[0] = 0;
|
||||||
|
lda #0
|
||||||
|
sta remainder
|
||||||
|
; for (int j = 16-1; j >= 0; j--)
|
||||||
|
ldx #QR_DEGREE-1
|
||||||
|
.loopJ
|
||||||
|
; result[j] ^= reedSolomonMultiply(generator[j], factor);
|
||||||
|
ldy .factor
|
||||||
|
IF QR_GENERATE
|
||||||
|
lda qrGenerator,x
|
||||||
|
jsr RSMult
|
||||||
|
ELSE
|
||||||
|
lda Generator,x
|
||||||
|
_RS_MULT
|
||||||
|
ENDIF
|
||||||
|
eor remainder,x
|
||||||
|
sta remainder,x
|
||||||
|
; }
|
||||||
|
dex
|
||||||
|
bpl .loopJ
|
||||||
|
; }
|
||||||
|
ldx .i
|
||||||
|
dex
|
||||||
|
bpl .loopI
|
||||||
|
ENDM
|
||||||
|
|
||||||
;-----------------------------------------------------------
|
;-----------------------------------------------------------
|
||||||
; Draws the raw codewords (including data and ECC) onto the given QR Code. This requires the initial state of
|
; Draws the raw codewords (including data and ECC) onto the given QR Code. This requires the initial state of
|
||||||
; the QR Code to be black at function modules and white at codeword modules (including unused remainder bits).
|
; the QR Code to be black at function modules and white at codeword modules (including unused remainder bits).
|
||||||
@ -546,6 +611,11 @@ QR_TOTAL = QR_MAX_DATA + QR_DEGREE ; 44
|
|||||||
; This is the main macro to use!
|
; This is the main macro to use!
|
||||||
QRCodeCode
|
QRCodeCode
|
||||||
|
|
||||||
|
IF QR_GENERATE
|
||||||
|
; generate the Reed-Solomon ECC generator polynomial
|
||||||
|
RSDevisor
|
||||||
|
_RS_DIVISOR
|
||||||
|
ENDIF
|
||||||
; calculate the ECC
|
; calculate the ECC
|
||||||
RSRemainder
|
RSRemainder
|
||||||
_RS_REMAINDER
|
_RS_REMAINDER
|
||||||
@ -677,6 +747,7 @@ FormatX2
|
|||||||
BitMask
|
BitMask
|
||||||
.byte $80, $40, $20, $10, $8, $4, $2, $1
|
.byte $80, $40, $20, $10, $8, $4, $2, $1
|
||||||
|
|
||||||
|
IF QR_GENERATE = 0
|
||||||
Generator ; data in reversed order!
|
Generator ; data in reversed order!
|
||||||
IF QR_DEGREE = 7
|
IF QR_DEGREE = 7
|
||||||
.byte $75, $44, $0b, $a4, $9a, $7a, $7f
|
.byte $75, $44, $0b, $a4, $9a, $7a, $7f
|
||||||
@ -726,6 +797,8 @@ Generator ; data in reversed order!
|
|||||||
|
|
||||||
QR_DEGREE = . - Generator ; verify data size
|
QR_DEGREE = . - Generator ; verify data size
|
||||||
|
|
||||||
|
ENDIF ; /QR_GENERATE
|
||||||
|
|
||||||
ECHO "QR Code encoding data:", [. - QRCodeData]d, "bytes"
|
ECHO "QR Code encoding data:", [. - QRCodeData]d, "bytes"
|
||||||
_QR_TOTAL SET _QR_TOTAL + . - QRCodeData
|
_QR_TOTAL SET _QR_TOTAL + . - QRCodeData
|
||||||
|
|
||||||
|
@ -39,11 +39,13 @@ NTSC = 1 ; 0 = PAL50
|
|||||||
; QR Code Generator Switches
|
; QR Code Generator Switches
|
||||||
QR_VERSION = 2 ; 1, 2 or 3 (TODO 1 and 3)
|
QR_VERSION = 2 ; 1, 2 or 3 (TODO 1 and 3)
|
||||||
QR_LEVEL = 1 ; 0 (L), 1 (M), 2 (Q) and 3 (H))
|
QR_LEVEL = 1 ; 0 (L), 1 (M), 2 (Q) and 3 (H))
|
||||||
QR_PADDING = 1 ; (+22) add padding bytes
|
QR_PADDING = 1 ; (+22 bytes) add padding bytes (optional)
|
||||||
|
QR_GENERATE = 1 ; (+~12 bytes) generates Reed-Solomon ECC generator polynomial on-the-fly
|
||||||
|
; else uses built-in table
|
||||||
|
|
||||||
; Atari 2600 specific QR settings (set to 0 for other platforms)
|
; Atari 2600 specific QR settings (set to 0 for other platforms)
|
||||||
QR_OVERLAP = 1 ; overlaps input and output data to save RAM (defined for version 2 only!)
|
QR_OVERLAP = 1 ; overlaps input and output data to save RAM (defined for version 2 only!)
|
||||||
QR_SINGLE_MASK = 0 ; (-255) if 1 uses only 1 of the 8 mask pattern
|
QR_SINGLE_MASK = 0 ; (-255 bytes) if 1 uses only 1 of the 8 mask pattern
|
||||||
|
|
||||||
IF QR_VERSION = 1 || QR_VERSION = 3
|
IF QR_VERSION = 1 || QR_VERSION = 3
|
||||||
ECHO ""
|
ECHO ""
|
||||||
@ -97,6 +99,9 @@ firstMsl = qrCodeLst + QR_SIZE * 1
|
|||||||
grp1Lst = qrCodeLst + NUM_FIRST + QR_SIZE * 1
|
grp1Lst = qrCodeLst + NUM_FIRST + QR_SIZE * 1
|
||||||
grp0RLst = qrCodeLst + NUM_FIRST + QR_SIZE * 2
|
grp0RLst = qrCodeLst + NUM_FIRST + QR_SIZE * 2
|
||||||
CODE_LST_SIZE = . - qrCodeLst
|
CODE_LST_SIZE = . - qrCodeLst
|
||||||
|
IF QR_GENERATE
|
||||||
|
qrGenerator ds QR_DEGREE
|
||||||
|
ENDIF
|
||||||
;---------------------------------------
|
;---------------------------------------
|
||||||
; QR code total = 89/127 bytes
|
; QR code total = 89/127 bytes
|
||||||
|
|
||||||
@ -218,8 +223,6 @@ CODE_LST_SIZE = . - qrCodeLst
|
|||||||
ENDIF
|
ENDIF
|
||||||
ENDM
|
ENDM
|
||||||
|
|
||||||
include QRCodeGen.inc
|
|
||||||
|
|
||||||
|
|
||||||
;===============================================================================
|
;===============================================================================
|
||||||
; R O M - C O D E
|
; R O M - C O D E
|
||||||
@ -308,6 +311,8 @@ DrawScreen SUBROUTINE
|
|||||||
rts
|
rts
|
||||||
; DrawScreen
|
; DrawScreen
|
||||||
|
|
||||||
|
include QRCodeGen.inc
|
||||||
|
|
||||||
;---------------------------------------------------------------
|
;---------------------------------------------------------------
|
||||||
Start SUBROUTINE
|
Start SUBROUTINE
|
||||||
;---------------------------------------------------------------
|
;---------------------------------------------------------------
|
||||||
|
Loading…
Reference in New Issue
Block a user