PR#3
PREFIX /A2OSX.SRC
NEW
INC 1
AUTO 6
				.LIST OFF
*--------------------------------------
* #K.NewPStrYA
*  Create a new copy of PSTR
* ##In:
*	Y,A = PTR to buffer
* ##Out:
*  CC : success 
*  Y,A = PTR to String
*  X = hMem (PSTRING)
*  CS : error
*  A = SYS error code
*--------------------------------------
K.NewPStrYA		>STYA ZPQuickPtr2
				lda (ZPQuickPtr2)
				inc
				tay
				lda #0					Y,A = len of new string
				>PUSHYA
				>PUSHBI 0				0 = no option
				jsr K.GetMem
				bcs .9

				>STYA ZPQuickPtr1

				jsr K.PStrCpyPtr2Ptr1
				
				>LDYA ZPQuickPtr1

				clc
.9				rts
*--------------------------------------
* #K.PStrCpy
*  Copy string
* ##In: 
*  PUSHW = PSTR to SRC (PSTRING)
*  PUSHW = PSTR to DST (PSTRING)
* ##Out: 
*  DST = SRC (PSTRING)
*--------------------------------------
K.PStrCpy		jsr PullPtr1Ptr2

K.PStrCpyPtr2Ptr1
				lda (ZPQuickPtr2)
				sta (ZPQuickPtr1)
				tay
				beq .2
				
.1				lda (ZPQuickPtr2),y
				sta (ZPQuickPtr1),y
				dey
				bne .1
				
.2				clc
				rts
*--------------------------------------
* #K.PStrCat
*  Append SRC to DST
* ##In: 
*  PUSHW = PSTR to SRC (PSTRING)
*  PUSHW = PSTR to DST (PSTRING)
* ##Out: 
*  DST = DST+SRC (PSTRING)
*--------------------------------------
K.PStrCat		jsr PullPtr1Ptr2
				
				lda (ZPQuickPtr2)
				tax
				
				lda (ZPQuickPtr1)
				tay
				
.1				cpy #255
				beq .8

				iny
				
				inc ZPQuickPtr2
				bne .2
				inc ZPQuickPtr1+1
				
.2				lda (ZPQuickPtr2)
				sta (ZPQuickPtr1),y
				dex
				bne .1
				
.8				tya
				sta	(ZPQuickPtr1)
				clc
				rts	
*/--------------------------------------
* #K.PStrMatch
*  Compare a String against pattern
* ##In: 
*   PUSHW = PTR to Pattern (e.g. '*test?.txt')
*   PUSHW = PTR to Src String 
* ##Out: 
*   CC : match
*	CS : no match
*\--------------------------------------
K.PStrMatch		jsr PullPtr1Ptr2

				lda (ZPQuickPTR2)		Keep Pattern Length in X 
                tax 
                beq .8                  Match always if empty 
				ldy #0

.1				inc ZPQuickPTR2			Make PTR1 advance to next char 
                bne .2 
				inc ZPQuickPTR2+1 

.2				lda (ZPQuickPTR2)       get pattern char 
				cmp #'*' 
				beq .5
                                        
.3				tya						we must match ? or regular char 
                cmp (ZPQuickPTR1)       check if at end of string 
                beq .9                  yes, no char left, exit with error 
                                        
				iny                     advance to next char to compare 
                                                
				lda (ZPQuickPTR2)       get back pattern char 
				cmp #'?' 
				beq .4                  no need to compare, any char will match 
				cmp (ZPQuickPTR1),y     Regular Char, compare with string at Y 
				bne .9                  no match, exit 
                                        
.4				dex 					char matched, check if end of pattern 
				bne .1					continue if remaining char in pattern 

				tya						end of pattern, but end of string ? 
				cmp (ZPQuickPTR1)       end of string ? 
				beq .8					yes, string matched entirely 
				bra .9					no, remaining char in string, no match 

.5				dex						we have '*', last char of pattern ? 
				beq .8					yes, match everything, including empty string 
                                        
				inc ZPQuickPTR2			Make PTR1 advance to next char 
				bne .6 
				inc ZPQuickPTR2+1 
                                        
.6				lda (ZPQuickPTR2)       get next char of pattern 
				cmp #'*'				another '*' ? 
				beq .5					yes, '**' = '*', go next char 
				cmp #'?'				'*?' ??? we must match a least one char 
				beq .3 
                                        
.7				tya						we need at least one remaining char in string, 
				cmp (ZPQuickPTR1)       check if at end of string 
				beq .9					no chance to match ? or regular char 
                                        
				iny 
				lda (ZPQuickPTR2)       get again char in pattern 
				cmp (ZPQuickPTR1),y 	compare with char in string 
                bne .7  	            not equal to next non wildcard in pattern 

				bra .4                  go check remaining char in pattern... 
                                        
.8				clc 
                rts 
                                        
.9              sec 
                rts 
*/--------------------------------------
* #K.PStrUprYA
*  Convert string to UPPERCASE
* #K.PStrLwrYA
*  Convert string to lowercase
* ##In:
*	Y,A = PTR to String (PSTRING)
* ##Out:
*   Uppercased/lowercased String in Buffer
*\--------------------------------------
K.PStrUprYA		ldx #0
				.HS 2C					bit abs
K.PStrLwrYA		ldx #2
				>STYA ZPQuickPtr1
				
				pha						save Y,A to restore them at exit
				phy
				
				lda (ZPQuickPtr1)
				tay
				
.1				lda (ZPQuickPtr1),y
				cmp K.PStrUprLwr,x
				bcc .2
				cmp K.PStrUprLwr+1,x
				bcs .2
				eor #$20
				sta (ZPQuickPtr1),y
.2				dey
				bne .1
				
				ply
				pla
				clc
				rts
*--------------------------------------
K.PStrUprLwr	.AS "azAZ"
*/--------------------------------------
* #K.PStrFTime
* Convert S.TIME struct to PSTR
* ##In : 
*  PUSHW = Dst PTR To PSTR Buf
*  PUSHW = Src PTR To Format String
*   %a Abbreviated weekday name : Thu
*	%A Full weekday name : Thursday 
*	%b Abbreviated month name : Aug 
*	%B Full month name : August 
*	%d Day of the month, zero-padded (01-31)
*	%H Hour in 24h format (00-23) 14 
*	%I Hour in 12h format (01-12) 02 
*	%m Month as a decimal number (01-12) 08 
*	%M Minute (00-59) 55 
*	%p AM or PM designation PM 
*	%S Second (00-61) 02 
*	%w Weekday as a decimal number with Sunday as 0 (0-6) 
*	%y Year, last two digits (00-99)
*	%Y Year four digits 2001 
*  PUSHW = Src PTR To S.Time
* ##Out :
*   none. always succeed.
*\--------------------------------------
K.PStrFTime		jsr PullPtr1Ptr2Ptr3
				
				lda #0
				sta (ZPQuickPtr3)		Reset target PSTR  length
				
				tay
				
.1				iny
				lda (ZPQuickPtr2),y
				cmp #'%'
				beq .2
				
				phy
				jsr K.PStrFTime.addChar
				ply
.10				tya
				cmp (ZPQuickPtr2)
				bne .1
				rts
				
.2				tya
				cmp (ZPQuickPtr2)
				beq .8
				
				iny
				ldx #K.PStrFTime.JMPL-K.PStrFTime.Tbl-1
				
.3				lda (ZPQuickPtr2),y
				cmp K.PStrFTime.Tbl,x
				beq .4
				dex
				bpl .3
				beq .10
				
.4				lda K.PStrFTime.JMPL,x
				sta .5+1
				lda K.PStrFTime.JMPH,x
				sta .5+2
				phy
.5				jsr $ffff
				ply
				bra .10

.8				rts			
*--------------------------------------
K.PStrFTime.TBL	.AS "aAbBdHImMpSwyY"
K.PStrFTime.JMPL .DA #K.PStrFTime.A
				.DA #K.PStrFTime.AA
				.DA #K.PStrFTime.B
				.DA #K.PStrFTime.BB
				.DA #K.PStrFTime.D
				.DA #K.PStrFTime.HH
				.DA #K.PStrFTime.II
				.DA #K.PStrFTime.M
				.DA #K.PStrFTime.MM
				.DA #K.PStrFTime.P
				.DA #K.PStrFTime.SS
				.DA #K.PStrFTime.W
				.DA #K.PStrFTime.Y
				.DA #K.PStrFTime.YY
*--------------------------------------
K.PStrFTime.JMPH	.DA /K.PStrFTime.A
				.DA /K.PStrFTime.AA
				.DA /K.PStrFTime.B
				.DA /K.PStrFTime.BB
				.DA /K.PStrFTime.D
				.DA /K.PStrFTime.HH
				.DA /K.PStrFTime.II
				.DA /K.PStrFTime.M
				.DA /K.PStrFTime.MM
				.DA /K.PStrFTime.P
				.DA /K.PStrFTime.SS
				.DA /K.PStrFTime.W
				.DA /K.PStrFTime.Y
				.DA /K.PStrFTime.YY
*--------------------------------------
K.PStrFTime.A	ldx #3					Short day of week, 3 chars...
				.HS	2C					Bit abs				
				 
K.PStrFTime.AA	ldx #15					full DoW
				>LDYAI K.PStrFTime.DAY
				>STYA ZPQuickPtr4		
				ldy #S.Time.WDAY
				bra K.PStrFTime.STR
				
K.PStrFTime.B	ldx #3					Short Month, 3 chars....
				.HS	2C					Bit abs
				
K.PStrFTime.BB	ldx #15					full Month....
				>LDYAI K.PStrFTime.MON
				>STYA ZPQuickPtr4		
				ldy #S.Time.MONTH
				
K.PStrFTime.STR	lda (ZPQuickPtr1),y 	get required S.Time field value
				tay
				beq .9					Illegal value
				
.1				dey						range 0..x
				beq .2
				lda (ZPQuickPtr4)
				sec
				adc ZPQuickPtr4
				sta ZPQuickPtr4
				bcc .1
				inc ZPQuickPtr4+1
				bra .1
				
.2				ldy #0

.3				iny
				lda (ZPQuickPtr4),y
				phy
				jsr K.PStrFTime.addChar
				pla
				cmp (ZPQuickPtr4)
				beq .8
				
				tay
				dex
				bne .3
.8				rts
				
.9				ldx #3
				lda #'?'
.99				jsr K.PStrFTime.addChar
				dex
				bne .99
				rts
				
K.PStrFTime.D	ldy #S.Time.DAY
				bra K.PStrFTime.addDecPtr1Y
K.PStrFTime.HH	ldy #S.Time.HOUR
				bra K.PStrFTime.addDecPtr1Y
K.PStrFTime.II	ldy #S.Time.HOUR
				lda (ZPQuickPtr1),y
				cmp #12
				bcc .1
				sbc #12
.1				bra K.PStrFTime.addDecA
K.PStrFTime.M	ldy #S.Time.MONTH
				bra K.PStrFTime.addDecPtr1Y
K.PStrFTime.MM	ldy #S.Time.MINUTE
				bra K.PStrFTime.addDecPtr1Y
K.PStrFTime.P	ldy #S.Time.HOUR
				lda (ZPQuickPtr1),y
				cmp #12
				bcc .1
				lda #'p'
				.HS 2C					bit abs
.1				lda #'a'
				jsr K.PStrFTime.addChar
				lda #'m'
				bra K.PStrFTime.addChar
K.PStrFTime.SS	ldy #S.Time.SECOND
				bra K.PStrFTime.addDecPtr1Y
K.PStrFTime.W	ldy #S.Time.WDAY
				bra K.PStrFTime.addDecPtr1Y
K.PStrFTime.YY	ldy #S.Time.CENTURY
				jsr K.PStrFTime.addDecPtr1Y
K.PStrFTime.Y	ldy #S.Time.YEAR
*--------------------------------------
K.PStrFTime.addDecPtr1Y
				lda (ZPQuickPtr1),y
K.PStrFTime.addDecA
				sta K.PStrFTime.BIN
				stz K.PStrFTime.DEC
				
				sed
				ldx #8
				
.1				asl K.PStrFTime.BIN

				lda K.PStrFTime.DEC
				adc K.PStrFTime.DEC
				sta K.PStrFTime.DEC
				
				dex
				bne .1
				
				cld

*				lda K.PStrFTime.DEC		already in A
				pha
				lsr
				lsr
				lsr
				lsr
				ora #$30
				jsr K.PStrFTime.addChar
				pla
				and #$0f
				ora #$30
*--------------------------------------
K.PStrFTime.addChar
				pha
				lda (ZPQuickPtr3)
				inc
				sta (ZPQuickPtr3)
				tay
				pla
				sta (ZPQuickPtr3),y
				rts
*--------------------------------------
K.PStrFTime.DAY	>PSTRING "Monday"
				>PSTRING "Tuesday"
				>PSTRING "Wednesday"
				>PSTRING "Thursday"
				>PSTRING "Friday"
				>PSTRING "Saturday"
				>PSTRING "Sunday"
*--------------------------------------
K.PStrFTime.MON	>PSTRING "January"
				>PSTRING "February"
				>PSTRING "March"
				>PSTRING "April"
				>PSTRING "May"
				>PSTRING "June"
				>PSTRING "July"
				>PSTRING "August"
				>PSTRING "September"
				>PSTRING "October"
				>PSTRING "November"
				>PSTRING "December"
*--------------------------------------
K.PStrFTime.BIN	.BS 1
K.PStrFTime.DEC	.BS 1					always < 100
*/--------------------------------------
* #K.PStr2StrArrayYA
* ##In : 
*  Y,A = PTR to String
* ##Out :
*  CC : success
*  Y,A = PTR to StrArray
*  X = hMem
*  CS : error
*  A = SYS error code
*\--------------------------------------
K.PStr2StrArrayYA
				>STYA ZPQuickPtr1
				lda (ZPQuickPtr1)		Get mem size STRLEN+1
				ldx #0
				inc
				bne .1
				inx
				
.1				>PUSHAX
				>PUSHBI 0
				jsr K.GetMem
				bcs .9
				phx					save hMem
				phy					save PTR.LO
				pha					save PTR.HI
				>STYA ZPQuickPtr2

				lda (ZPQuickPtr1)
				tax					count in src string
				beq .8
				
				ldy #0				reset index in dst token

.3				inc ZPQuickPtr1		get...
				bne .4
				inc ZPQuickPtr1+1
.4				lda (ZPQuickPtr1)	...next char

				cmp #' '			found a space ?
				bne .6
				
				tya					in a token ?
				beq .7				no, skip & go to next char
				
				sta (ZPQuickPtr2)	yes, set this token len
				sec
				adc ZPQuickPtr2		advance to next token
				sta ZPQuickPtr2
				bcc .5
				inc ZPQuickPtr2+1
				
.5				ldy #0				reset index in dst token
				bra .7
				
.6				iny					add char to token
				sta (ZPQuickPtr2),y
				
.7				dex					end of src string?
				bne .3				no...next char...
				
				tya					yes, are we in a token ?
				beq .8
				
				sta (ZPQuickPtr2)	yes, set last token len
				sec
				adc ZPQuickPtr2		advance to next token
				sta ZPQuickPtr2
				bcc .8
				inc ZPQuickPtr2+1
				
.8				lda #0
				sta (ZPQuickPtr2)	set Array Ending 0
				
				pla					get back PTR.HI
				ply					get back PTR.LO
				plx					get back hMem
				clc
.9				rts				
*--------------------------------------
MAN
SAVE SYS/KERNEL.S.STR
LOAD SYS/KERNEL.S
ASM
