NEW
  AUTO 3,1
				.LIST OFF
				.OP	65C02
				.OR	$2000
				.TF SBIN/HTTPD
*--------------------------------------
				.INB INC/MACROS.I
				.INB INC/A2OSX.I
				.INB INC/ETH.I
				.INB INC/LIBTCPIP.I
				.INB INC/NET.HTTP.I
*--------------------------------------
TIMEOUT.MAX		.EQ 30					30 sec.
CONN.MAX		.EQ 16
*--------------------------------------
				.DUMMY
				.OR ZPBIN
ZS.START
ZPIPCfgPtr		.BS 2
ZPSktPtr		.BS 2
ZPMsgPtr		.BS 2
ZPMsgDataPtr	.BS 2
ZPMsgDataLen	.BS 2
ZPMsgDataCnt	.BS 2

ArgIndex		.BS 1
hRootdir		.BS 1
ZPRootDirPtr	.BS 2
ZPStrPtr		.BS 2

hSrvSocket		.BS 1
hClntSocket		.BS 1
hMsg			.BS 1
hStr			.BS 1
TimeOut			.BS 1

ZS.END			.ED
*--------------------------------------
*			File Header (16 Bytes)
*--------------------------------------
CS.START		cld
				jmp (.1,x)
				.DA #$61				6502,Level 1 (65c02)
				.DA #1					BIN Layout Version 1
				.DA #S.PS.F.EVENT
				.DA #0
				.DA CS.END-CS.START		CS
				.DA DS.END-DS.START		DS
				.DA #64					SS
				.DA #ZS.END-ZS.START	Zero Page Size
				.DA 0
*--------------------------------------
* Relocation Table
*--------------------------------------
.1				.DA CS.INIT
				.DA CS.RUN
				.DA CS.DOEVENT
				.DA	CS.QUIT
L.LIBTCPIP		.DA LIBTCPIP
L.SA.Local		.DA SA.Local
L.MSG.TCPWAIT	.DA MSG.TCPWAIT
L.MSG.TCPIPERR	.DA MSG.TCPIPERR
L.MSG.INITOK	.DA MSG.INITOK
L.MSG.SKTERR	.DA MSG.SKTERR
L.MSG.INCOMING	.DA MSG.INCOMING
L.HTTP.200OK	.DA HTTP.200OK
				.DA 0
*--------------------------------------
CS.INIT			>LDYA L.LIBTCPIP
				>SYSCALL LoadLib
				bcs .9
				sta hLIBTCPIP

.9				rts
*--------------------------------------
CS.RUN			>LDYA L.MSG.TCPWAIT
				>SYSCALL puts

				lda #TIMEOUT.MAX
				sta TimeOut
				
.1				>SLEEP
				>LIBCALL hLIBTCPIP,LIBTCPIP.GETCFG	is TCPIP loaded ?
				bcs .99

				>STYA ZPIPCfgPtr
				lda (ZPIPCfgPtr)		Configured ?
				bmi CS.RUN.INIT

				lda Timeout
				bcs .99

				ldy #S.PS.hStdIn
				lda (pPs),y
				>SYSCALL feof
				bcs CS.RUN.RTS			I/O err
				tay
				bne .1

				>SYSCALL GetChar
				bcs CS.RUN.RTS

				cmp #$03
				bne .1

				sec
				rts

.99				>LDYA L.MSG.TCPIPERR
				>SYSCALL puts
CS.RUN.SYN
				lda #E.SYN
				sec	
CS.RUN.RTS		rts

CS.RUN.INIT		ldx #3
				ldy #S.IPCFG.IP+3

.1				lda (ZPIPCfgPtr),y
				sta SA.LOCAL+S.SOCKADDR.ADDR,x
				dey
				dex
				bpl .1

				lda #1
				sta ArgIndex
				
				>SYSCALL ArgV
				bcs CS.RUN.SYN
				>SYSCALL atoi
				bcs .2

				>STYA SA.LOCAL+S.SOCKADDR.PORT
				inc ArgIndex

.2				lda ArgIndex
				>SYSCALL ArgV
				bcs CS.RUN.SYN

				>PUSHYA
				>PUSHWI 0				Allocate
				>SYSCALL realpath
				bcs CS.RUN.RTS
				
				>STYA ZPRootDirPtr

CS.RUN.ARGSOK	>PUSHBI 0				no protocol
				lda #S.SOCKET.T.SEQPACKET
				>LIBCALL hLIBTCPIP,LIBTCPIP.Socket
				bcs CS.RUN.ERR

				sta hSrvSocket

				>PUSHW L.SA.LOCAL
				lda hSrvSocket
				>LIBCALL hLIBTCPIP,LIBTCPIP.Bind
				bcs CS.RUN.ERR
				
				lda hSrvSocket
				>LIBCALL hLIBTCPIP,LIBTCPIP.Listen
				bcs CS.RUN.ERR

				>LDYAI 256
				>SYSCALL getmem
				bcs CS.RUN.ERR
				
				>STYA ZPStrPtr
				stx hStr
				
				>PUSHW L.MSG.INITOK
				>PUSHW SA.LOCAL+S.SOCKADDR.PORT
				>PUSHW ZPRootDirPtr
				>PUSHBI 4 
				
				>SYSCALL printf

CS.RUN.LOOP		>SLEEP
				jsr CS.RUN.SERVER
				bcs CS.RUN.ERR
				bra CS.RUN.LOOP

.9				>LDYA L.MSG.SKTERR
				>SYSCALL puts
				lda #E.SYN
				sec	
CS.RUN.ERR		rts
*--------------------------------------
CS.RUN.SERVER	lda hSrvSocket
				>LIBCALL hLIBTCPIP,LIBTCPIP.accept
				bcs .8
				
				sta hClntSocket
				>SYSCALL GetMemPtr
				>STYA ZPSktPtr

				>PUSHW L.MSG.INCOMING

				ldx #3
				ldy #S.SOCKET.REM.ADDR

				>PUSHB hClntSocket

.1				>PUSHB (ZPSktPtr),y
				iny
				dex
				bpl .1

				>PUSHBI 5
				>SYSCALL printf

				jsr CS.RUN.CLIENT
.8				clc
.9				rts
*--------------------------------------
CS.RUN.CLIENT	
.1				>SLEEP

				>LIBCALL hLIBTCPIP,LIBTCPIP.Recv
				bcc .2

				tay
				beq .1
				bra .8

.2				jsr CS.RUN.MSG.INIT

.3				jsr CS.RUN.MSG.GetStr
				bcs .7

				>PUSHYA
				>PUSHW ZPStrPtr
				ldy #S.PS.hStdOut
				lda (pPS),y

				>SYSCALL fwrite
				bra .3

				lda hMsg
				>SYSCALL freemem

.7				>PUSHWI HTTP.200OK.len
				>PUSHW L.HTTP.200OK
				lda hClntSocket
				>LIBCALL hLIBTCPIP,LIBTCPIP.Send
				
.8				lda hClntSocket
				>LIBCALL hLIBTCPIP,LIBTCPIP.Shutdown

				clc
				rts
*--------------------------------------
CS.RUN.MSG.INIT	sta hMsg
				>SYSCALL getmemptr
				>STYA ZPMsgPtr
				pha
				tya
*				clc
				adc #S.TCP
				sta ZPMsgDataPtr
				
				pla
				adc /S.TCP
				sta ZPMsgDataPtr+1
				
				ldy #S.IP.TOTAL.LENGTH+1
				lda (ZPMsgPtr),y
				sec
				sbc #S.IP
				sta ZPMsgDataLen
				eor #$ff
				sta ZPMsgDataCnt
				
				dey
				lda (ZPMsgPtr),y
				sbc /S.IP
				sta ZPMsgDataLen+1
				eor #$ff
				sta ZPMsgDataCnt+1

				rts
*--------------------------------------
CS.RUN.MSG.GetStr
				ldy #0

.1				inc ZPMsgDataCnt
				bne .2
				inc ZPMsgDataCnt+1
				beq .9

.2				lda (ZPMsgDataPtr)
				inc ZPMsgDataPtr
				bne .21
				inc ZPMsgDataPtr+1
				
.21				cmp #C.CR
				bne .4
				
				inc ZPMsgDataCnt
				bne .3
				inc ZPMsgDataCnt+1
				beq .9
				
.3				lda (ZPMsgDataPtr)
				inc ZPMsgDataPtr
				bne .31
				inc ZPMsgDataPtr+1

.31				eor #C.LF
				bne .9

				sta (ZPStrPtr),y		Y,A = StrLen
				clc
				rts
				
.4				sta (ZPStrPtr),y
				iny
				bra .1
				
.9				sec
				rts
*--------------------------------------
CS.DOEVENT		lda (pEvent)
				bpl .9					is it a TIMER event?
				lda TimeOut
				beq .9
				dec TimeOut

.9				sec						do not discard TIMER event
				rts
*--------------------------------------
CS.QUIT			lda hSrvSocket
				beq .3
				
				>LIBCALL hLIBTCPIP,LIBTCPIP.Shutdown

.3				lda hLIBTCPIP
				beq .8

				>SYSCALL UnloadLib

.8				clc
				rts
*--------------------------------------
CS.END
*--------------------------------------
hLIBTCPIP		.BS 1
LIBTCPIP		.AZ "libtcpip"
MSG.TCPWAIT		.AZ "HTTPD:Waiting for TCP/IP initializing..."
MSG.TCPIPERR	.AZ "HTTPD:TCP/IP Not initialized properly."
MSG.INITOK		.AZ "HTTPD:Listening on port %D, root dir: %s.\r\n"
MSG.SKTERR		.AZ "HTTPD:Listen Error."
MSG.INCOMING	.AZ "HTTPD:Incoming Connection [SKT=%h] From : %d.%d.%d.%d\r\n"
*--------------------------------------
HTTP.200OK		.AS "HTTP/1.1 200 OK"
				.DA #C.CR,#C.LF
				.AS "Server: A2osX-HTTPD 0.93"
				.DA #C.CR,#C.LF
				.AS "Content-Type: text/html"
				.DA #C.CR,#C.LF
				.AS "Content-Length: 34"
				.DA #C.CR,#C.LF
				.AS "Connection: Close"
				.DA #C.CR,#C.LF
				.DA #C.CR,#C.LF
				.AS "<HTML><BODY>Hello From A2osX-HTTPD 0.93 !</BODY></HTML>"
				.DA #C.CR,#C.LF
HTTP.200OK.len	.EQ *-HTTP.200OK
*--------------------------------------
SA.LOCAL		.DA #AF.INET			S.SOCKADDR.AF
				.BS 1
				.BS 4					S.SOCKADDR.ADDR
				.DA TCP.PORT.HTTP
*--------------------------------------
				.DUMMY
				.OR 0
DS.START
DS.END
				.ED
*--------------------------------------
MAN
SAVE USR/SRC/SBIN/HTTPD.S
ASM
