Code archives/User Input/COM-Port

This code has been declared by its author to be Public Domain code.

Download source code

COM-Port by Vertex2004
The original code are from http://www.c-plus-plus-archiv.de/archiv/show.ca/title/Kommunikation%20%FCber%20RS232/author/Stefan%20Schneider/file/RS232.cpp/?offset=0&noclass=&nolist=&sort=downloads&dir=up&type=

How to use?
openComport(comPort, baudRate):
Create a device and return the handle of it.
If you use a false baudrate or a false comportindex, then the function return FALSE or if the device can't open, then return the function -1. Else the function return a valid handle of the device.

closeComport(driverHandle)
Close the comport.
If the driverHandle a invalid handle, then the function return FALSE, alse the return value is nonzero.

writeComport(driverHandle, numBytes, buffer)
Transmit datas.
numByte are the number of bytes to transmit.
buffer is the handle of a bank, that includes the datas.
If the function fails, then the return value is FALSE else a nonzero value.

readComport(driverHandle, bytesRead, bufferSize, buffer, tOut)
Reveive datas
bytesRead is a bank with a size of 4 Bytes
bufferSize is the size of the buffer
buffer is a bank to save the received datas
tOut is the timeout in millisecs
If the function succeeds, then the return value is TRUE else FALSE. The number of bytes that received saved in the bytesRead bank as integervalue.

cu olli
Const  parityEnable        = False ; flag if parity is enabled
Const  protocol            = 0     ; stores protocol type
Const  dataBits            = 8     ; stores number if data bits
Const  parityBit           = 0     ; stores type of parity bit
Const  stopBits            = 0     ; stores number of stop bits
Global timeouts            = CreateBank(20)

Const INVALID_HANDLE_VALUE = -1

Const  GENERIC_READ        = $80000000
Const  GENERIC_WRITE       = $40000000
Const  OPEN_EXISTING       = 3

Const  CBR_110             = 110
Const  CBR_300             = 300
Const  CBR_600             = 600
Const  CBR_1200            = 1200
Const  CBR_2400            = 2400
Const  CBR_4800            = 4800
Const  CBR_9600            = 9600
Const  CBR_14400           = 14400
Const  CBR_19200           = 19200
Const  CBR_38400           = 38400
Const  CBR_56000           = 56000
Const  CBR_57600           = 57600
Const  CBR_115200          = 115200

Const  DTR_CONTROL_DISABLE = 0
Const  DTR_CONTROL_ENABLE  = 1
Const  RTS_CONTROL_DISABLE = 0
Const  RTS_CONTROL_ENABLE  = 1
Const  EV_TXEMPTY          = 4

Const  SETRTS              = 3
Const  CLRRTS              = 4

; Example ---------------------------------------------------------------------------
Print "Open COM1 with 9600 baudrate ..."
hCom = openComport(1, 9600)
If hCom <> 0 Then
	Print "   Succesfully"
Else
	Print "   Error"
	WaitKey : End
EndIf


; Transmit:
buffer = CreateBank(6)
PokeByte buffer, 0, Asc("H")
PokeByte buffer, 1, Asc("e")
PokeByte buffer, 2, Asc("l")
PokeByte buffer, 3, Asc("l")
PokeByte buffer, 4, Asc("o")
PokeByte buffer, 5, 0
Print "Sending "+Chr$(34)+"Hello"+Chr$(34)+" ..."
If writeComPort(hCom, 6, buffer) Then
	Print "   Succesfully"
Else
	Print "   Error"
	closeComport(hCom)
	WaitKey : End
EndIf
FreeBank buffer

; Receive
buffer = CreateBank(1024)
bytes  = CreateBank(4)
Print "Receiving datas ..."
If readComport(hCom, bytes, 1024, buffer, 10000) Then ; 10 Sekunden timeout
	Print "   Succesfully"
	Print "   Number of receiving bytes "+PeekInt(bytes, 0)
	; Datas are in the bank buffer
Else
	Print "   Error"
EndIf

; Close and end
closeComport(hCom)
WaitKey : End
; -----------------------------------------------------------------------------------

Function openComport(comport, baudRate)
   Local dcbBaudRate, driverHandle, dcb
   
   If comport > 255 Or comport < 0 Then
      Return False
   EndIf
   
   Select baudRate
      Case 110
         dcbBaudRate = CBR_110
      Case 300
         dcbBaudRate = CBR_300
      Case 600
         dcbBaudRate = CBR_600
      Case 1200
         dcbBaudRate = CBR_1200
      Case 2400
         dcbBaudRate = CBR_2400
      Case 4800
         dcbBaudRate = CBR_4800
      Case 9600
         dcbBaudRate = CBR_9600
      Case 14400
         dcbBaudRate = CBR_14400
      Case 19200
         dcbBaudRate = CBR_19200
      Case 38400
         dcbBaudRate = CBR_38400
      Case 56000
         dcbBaudRate = CBR_56000
      Case 57600
         dcbBaudRate = CBR_57600
      Case 115200
         dcbBaudRate = CBR_115200
      Default
         Return False
   End Select
   
   driverHandle = apiCreateFile("COM"+comport, GENERIC_READ Or GENERIC_WRITE, 0, 0, OPEN_EXISTING, 0, 0)
   If driverHandle = INVALID_HANDLE_VALUE Then
      Return INVALID_HANDLE_VALUE
   Else
      apiSetupComm(driverHandle, 1024, 1024)
      dcb = CreateBank(80)
      PokeInt dcb, 00, 80                         ; sizeof(DCB)
      PokeInt dcb, 04, dcbBaudRate                ; current baud rate
      PokeInt dcb, 08, 1                          ; binary mode, no EOF check
      If parityEnable = True Then
         PokeInt dcb, 12, 1                       ; enable parity checking
      Else
         PokeInt dcb, 12, 0                       ; disable parity checking
      EndIf
      If protocol = 0 Then
         PokeInt dcb, 24, DTR_CONTROL_ENABLE      ; DTR flow control type
      Else
         PokeInt dcb, 24, DTR_CONTROL_DISABLE     ; DTR flow control type
      EndIf
      PokeInt dcb, 28, False                      ; DSR sensitivity
      If protocol = 1 Then
         PokeInt dcb, 52, RTS_CONTROL_ENABLE      ; RTS flow control
      Else
         PokeInt dcb, 52, RTS_CONTROL_DISABLE     ; RTS flow control
      EndIf
      PokeInt  dcb, 60, 17                        ; reserved
      PokeByte dcb, 70, dataBits                  ; number of bits/byte, 4-8
      PokeByte dcb, 71, parityBit                 ; 0-4=no, odd, even, mark, space
      PokeByte dcb, 72, stopBits                  ; 0,1,2 = 1, 1.5, 2
      
      apiSetCommState(driverHandle, dcb)
      apiSetCommMask(driverHandle, EV_TXEMPTY)
   EndIf
   
   FreeBank dcb
   Return driverHandle
End Function

Function closeComport(driverHandle)
   If driverHandle = INVALID_HANDLE_VALUE Or driverHandle = 0 Then
      Return False
   Else
      Return apiCloseHandle(driverHandle)
   EndIf
End Function

Function writeComport(driverHandle, numBytes, buffer)
   Local state, temp

   If driverHandle = INVALID_HANDLE_VALUE Or driverHandle = 0 Then
      Return False
   EndIf
   
   apiEscapeCommFunction(driverHandle, SETRTS)
   
   temp = CreateBank(4)
   state = apiWriteFile(driverHandle, buffer, numBytes, temp, 0)
   
   apiEscapeCommFunction(driverHandle, CLRRTS)
   
   FreeBank temp
   Return state
End Function

Function readComport(driverHandle, bytesRead, bufferSize, buffer, tOut)
	Local comErrors, comStat
	
   If driverHandle = INVALID_HANDLE_VALUE Or driverHandle = 0 Then
      Return False
   EndIf
	
	PokeInt timeouts, 00, 0
	PokeInt timeouts, 04, 0
	PokeInt timeouts, 08, tOut
	PokeInt timeouts, 12, 0
	apiSetCommTimeouts(driverHandle, timeouts)
	
	comErrors = CreateBank(4)
	comStat   = CreateBank(10)
	apiClearCommError(driverHandle, comErrors, comStat)
	
	apiReadFile(driverHandle, buffer, bufferSize, bytesRead, 0)
	
	FreeBank comErrors
	FreeBank comStat
	Return True
End Function

Comments

Vertex2004
Sorry i have forgot the decls:
.lib "Kernel32.dll"
apiCreateFile%(lpFileName$, dwDesiredAccess, dwShareMode, lpSecurrityAttributes, dwCreationDistribution, dwFlagsAndAttributes, hTemplateFile) : "CreateFileA"
apiSetupComm%(hFile, dwInQueue, dwOutQueue)                                                                                                   : "SetupComm"
apiGetCommState%(hFile, lpDCB*)                                                                                                               : "GetCommState"
apiSetCommState%(hFile, lpCDB*)                                                                                                               : "SetCommState"
apiSetCommMask%(hFile, dwEvtMask)                                                                                                             : "SetCommMask"
apiCloseHandle%(hObject)                                                                                                                      : "CloseHandle"
apiEscapeCommFunction%(hFile, dwFunc)                                                                                                         : "EscapeCommFunction"
apiWriteFile%(hFile, lpBuffer*, nNumberOfBytesToWrite, lpNumberOfBytesWritten*, lpOverlapped)                                                 : "WriteFile"
apiSetCommTimeouts%(hFile, lpCommTimeouts*)                                                                                                   : "SetCommTimeouts"
apiClearCommError%(hFile, lpErrors*, lpStat*)                                                                                                 : "ClearCommError"
apiReadFile%(hFile, lpBuffer, nNumberOfBytesToRead, lpNumberOfBytesRead*, lpOverlapped)                                                       : "ReadFile"

And the
hCom = openComport(1, 9600)
If hCom <> 0 Then
   Print "   Succesfully"
Else
   Print "   Error"
   WaitKey : End
EndIf

must be replace to
hCom = openComport(1, 9600)
If hCom <> 0 and hCOM <> INVALID_HANDLE_VALUE Then
   Print "   Succesfully"
Else
   Print "   Error"
   WaitKey : End
EndIf

cu olli


Nigel Brown2004
Am having trouble reading data from read buffer get an abnormal program termination if i try and read from the buffer with "PeekByte(buffer,0)" or release the buffer with "FreeBank buffer" ?


Vertex2004
Hi!
Oh sorry yes,
apiReadFile%(hFile, lpBuffer, nNumberOfBytesToRead, lpNumberOfBytesRead*, lpOverlapped) : "ReadFile"
must be
apiReadFile%(hFile, lpBuffer*, nNumberOfBytesToRead, lpNumberOfBytesRead*, lpOverlapped) : "ReadFile"

So the function has only poke datas in the BlitzBankStructure and has overwrite the pointer to the memoryblock.

cu olli


Nigel Brown2004
none of the word control settings ie: dataBits,parityBit,stopBits seem to make any difference when you change thier values? this means it is dependent on the port being set correctly by something else! I have checked this on a logic analyzer.


Vertex2004
Hmmm if you set the parityBit, then the receiverhardware can use this as a checksum. The stopBits can be 1, 1.5, 2. This stopBit will be add at the end on a transmited value. But i can't test it. I have only here a 56k Modem to test, but it doesn't reacted on simply AT-Commandos like "ATL3" or "ATDT 0123456789"(but i can see, that the modem receive datas).
cu olli


Nigel Brown2004
there seems to be 7 data bits sent rather than the 8 required and asked for by the setting of dataBits. After running another piece of software that sets data bits to 8 all is well.
This suggests to me that the dataBits setting is having no effect. I did wonder about the offset into the dcb but calculated it at the same offset as you?


skidracer2004
I think you need to test the SetCommState return value to see whether you are making any difference to the port settings or not. I set the dcblength, call GetCommState then alter the relevant values and then call SetCommState, testing it's return value for success.


Nigel Brown2004
Ok get what youre trying to say i think. I believe the following should set then read back 8 data bits. On my machine it returns 0 data bits? Tell me I am doing something wrong please!


Const INVALID_HANDLE_VALUE = -1

Const  GENERIC_READ        = $80000000
Const  GENERIC_WRITE       = $40000000
Const  OPEN_EXISTING       = 3
Const  EV_TXEMPTY          = 4

	driverHandle = apiCreateFile("COM1", GENERIC_READ Or GENERIC_WRITE, 0, 0, OPEN_EXISTING, 0, 0)

	; Create DCB
	dcb = CreateBank(80)
	PokeInt dcb, 0, 80							; sizeof(DCB)
	
	; Get the Comm state
	apiGetCommState(driverHandle, dcb )
	Print PeekByte(dcb,70)						; should return ?

	; Set dataBits
	PokeByte dcb, 70, 8							; number of bits/byte, 4-8

	; Set comm state
	apiSetCommState(driverHandle, dcb)
	apiSetCommMask(driverHandle, EV_TXEMPTY)



	; Create another DCB and read result into it		
	dcb2 = CreateBank(80)
	PokeInt dcb2, 0, 80							; sizeof(DCB)
	
	; Read result into new DCB
	apiGetCommState(driverHandle, dcb2 )
	Print PeekByte(dcb2,70)						; should return 8


	WaitKey()




Vertex2004
Yes, i get too a succeedvalue but ByteSize remains the same value. A athor method is possibly too use BuildCommDCB:
apiBuildCommDCB%(lpDef$, lpDCB*) : "BuildCommDCB"

here the quote of the WinAPI:
The BuildCommDCB function fills a specified DCB structure with values specified in a device-control string. The device-control string uses the syntax of the mode command.

BOOL BuildCommDCB(

LPCTSTR lpDef, // pointer to device-control string
LPDCB lpDCB // pointer to device-control block
);


Parameters

lpDef

Pointer to a null-terminated string that specifies device-control information. The string must have the same form as the mode command's command-line arguments. For example, the following string specifies a baud rate of 1200, no parity, 8 data bits, and 1 stop bit:

baud=1200 parity=N data=8 stop=1


The device name is ignored if it is included in the string, but it must specify a valid device, as follows:

COM1: baud=1200 parity=N data=8 stop=1


For further information on mode command syntax, refer to the end-user documentation for your operating system.

lpDCB

Pointer to a DCB structure to be filled in.



Return Values

If the function succeeds, the return value is nonzero.
If the function fails, the return value is zero. To get extended error information, call GetLastError.

Remarks

The BuildCommDCB function adjusts only those members of the DCB structure that are specifically affected by the lpDef parameter, with the following exceptions:

· If the specified baud rate is 110, the function sets the stop bits to 2 to remain compatible with the Windows NT or MS-DOS mode command.
· By default, BuildCommDCB disables XON/XOFF and hardware flow control. To enable flow control, you must explicitly set the appropriate members of the DCB structure.



The BuildCommDCB function only fills in the members of the DCB structure. To apply these settings to a serial port, use the SetCommState function.
There are older and newer forms of the mode command syntax. The BuildCommDCB function supports both forms. However, you cannot mix the two forms together.
The newer form of the mode command syntax lets you explicitly set the values of the flow control members of the DCB structure. If you use an older form of the mode syntax, the BuildCommDCB function sets the flow control members of the DCB structure, as follows:

· For a string such as 96,n,8,1 or any other older-form mode string that doesn't end with an x or a p:

fInX, fOutX,fOutXDsrFlow,and fOutXCtsFlow are all set to FALSE
fDtrControl is set to DTR_CONTROL_ENABLE
fRtsControl is set to RTS_CONTROL_ENABLE

· For a string such as 96,n,8,1,x or any other older-form mode string that finishes with an x:

fInX, fOutX are both set to TRUE
fOutXDsrFlow,fOutXCtsFlow are both set to FALSE.
fDtrControl is set to DTR_CONTROL_ENABLE
fRtsControl is set to RTS_CONTROL_ENABLE

· For a string such as 96,n,8,1,p or any other older-form mode string that finishes with a p:

fInX, fOutX are both set to FALSE
fOutXDsrFlow,fOutXCtsFlow are both set to TRUE.
fDtrControl is set to DTR_CONTROL_HANDSHAKE
fRtsControl is set to RTS_CONTROL_HANDSHAKE



See Also

DCB, SetCommState

cu olli


Nigel Brown2004
a working example please, one that tests the results.


skidracer2004
try this one:

Const INVALID_HANDLE_VALUE = -1

Const  GENERIC_READ        = $80000000
Const  GENERIC_WRITE       = $40000000
Const  OPEN_EXISTING       = 3
Const  EV_TXEMPTY          = 4

driverHandle = apiCreateFile("COM1", GENERIC_READ Or GENERIC_WRITE, 0, 0, OPEN_EXISTING, 0, 0)

Print "handle="+driverhandle

; Create DCB

dcb = CreateBank(28)
PokeInt dcb, 0, 28 ; sizeof(DCB)
	
; Get the Comm state

apiGetCommState(driverHandle,dcb)
Print PeekByte(dcb,18)  ; print data bits

WaitKey()



Nigel Brown2004
Yes that returns a numeric handle, and also the value 8 but the offset into the DCB is 18 the offset used in the previous prog for dataBits was 70, look's like thats the problem the offsets are incorrect

What is going on?

The offsets for the DCB at offset 8 are bits not DWORDS.


;typedef struct _DCB {
; DWORD DCBlength; /* sizeof(DCB) */ = 0 = 28
; DWORD BaudRate; /* Baudrate at which running */ = 4
; DWORD fBinary: 1; /* Binary Mode (skip EOF check) */ = 8
; DWORD fParity: 1; /* Enable parity checking */ =
; DWORD fOutxCtsFlow:1; /* CTS handshaking on output */ =
; DWORD fOutxDsrFlow:1; /* DSR handshaking on output */ =
; DWORD fDtrControl:2; /* DTR Flow control */ =
; DWORD fDsrSensitivity:1; /* DSR Sensitivity */ =
; DWORD fTXContinueOnXoff: 1; /* Continue TX when Xoff sent */ =
; DWORD fOutX: 1; /* Enable output X-ON/X-OFF */ =
; DWORD fInX: 1; /* Enable input X-ON/X-OFF */ =
; DWORD fErrorChar: 1; /* Enable Err Replacement */ =
; DWORD fNull: 1; /* Enable Null stripping */ =
; DWORD fRtsControl:2; /* Rts Flow control */ =
; DWORD fAbortOnError:1; /* Abort all reads and writes on Error */ =
; DWORD fDummy2:17; /* Reserved */ =
; WORD wReserved; /* Not currently used */ = 12
; WORD XonLim; /* Transmit X-ON threshold */ = 14
; WORD XoffLim; /* Transmit X-OFF threshold */ = 16
; BYTE ByteSize; /* Number of bits/byte, 4-8 */ = 18
; BYTE Parity; /* 0-4=None,Odd,Even,Mark,Space */ = 19
; BYTE StopBits; /* 0,1,2 = 1, 1.5, 2 */ = 20
; char XonChar; /* Tx and Rx X-ON character */ = 21
; char XoffChar; /* Tx and Rx X-OFF character */ = 22
; char ErrorChar; /* Error replacement char */ = 23
; char EofChar; /* End of Input character */ = 24
; char EvtChar; /* Received Event character */ = 25
; WORD wReserved1; /* Fill for now. */ = 26
;
;} DCB, *LPDCB;


Nigel Brown2004
Think this is a valid replacement for the openComport supplied above, will fix any bugs if any :-)

Function openComport(comport, baudRate)

	Local dcbBaudRate, driverHandle, dcb
   
	If comport > 255 Or comport < 0 Then
		Return INVALID_HANDLE_VALUE
	EndIf
   
	Select baudRate
		Case 110
			dcbBaudRate = CBR_110
		Case 300
			dcbBaudRate = CBR_300
		Case 600
			dcbBaudRate = CBR_600
		Case 1200
			dcbBaudRate = CBR_1200
		Case 2400
			dcbBaudRate = CBR_2400
		Case 4800
			dcbBaudRate = CBR_4800
		Case 9600
			dcbBaudRate = CBR_9600
		Case 14400
			dcbBaudRate = CBR_14400
		Case 19200
			dcbBaudRate = CBR_19200
		Case 38400
			dcbBaudRate = CBR_38400
		Case 56000
			dcbBaudRate = CBR_56000
		Case 57600
			dcbBaudRate = CBR_57600
		Case 115200
			dcbBaudRate = CBR_115200
		Default
			Return INVALID_HANDLE_VALUE
	End Select
	
	driverHandle = apiCreateFile("COM"+comport, GENERIC_READ Or GENERIC_WRITE, 0, 0, OPEN_EXISTING, 0, 0)
	If driverHandle = INVALID_HANDLE_VALUE Then
		Return INVALID_HANDLE_VALUE
	Else
		apiSetupComm(driverHandle, 1024, 1024)

		dcb = CreateBank(28)
		
		PokeInt dcb, 00, 28                         ; sizeof(DCB)
		PokeInt dcb, 04, dcbBaudRate                ; current baud rate

		val	= 1										; Binary Mode (skip Eof check)    
		If parityEnable	= True Then val = val Or 2	; Enable parity checking
		If protocol		= DTR_CONTROL Then val = val Or 48	; DTR Flow control on
		PokeByte dcb, 08, val
		
		val = 0
		If protocol = RTS_CONTROL Then val = val Or 48
		PokeByte dcb, 09, val

		PokeByte dcb, 18, dataBits					; number of bits/byte, 4-8
		PokeByte dcb, 19, parityBit					; 0-4=no, odd, even, mark, space
		PokeByte dcb, 20, stopBits					; 0,1,2 = 1, 1.5, 2

		apiSetCommState(driverHandle, dcb)
		apiSetCommMask(driverHandle, EV_TXEMPTY)

	EndIf
   
	FreeBank dcb
	Return driverHandle
	
End Function





skidracer2004
Nigel, note the :1 etc. bit field operators.


Nigel Brown2004
thanks skidracer, I think that was what I said 2 posts ago?

"What is going on? The offsets for the DCB at offset 8 are bits not DWORDS."

Or were you hinting at a bug you may have found?


MErren2004
Hello Vertex,
can you help me
I know the out comand and wan't to translate the following code to BB.
10 BA=&H2F8 : REM COM2
20 OUT (BA+3), 64
30 CLS
40 PRINT " SERAI812 an COM2
100 REM Messung an 8 Kan?len
110 LOCATE 10,1
120 FOR N= 0 TO 7
130 SEL = 7-(N\2) -4*(N AND 1)
140 GOSUB 500
150 PRINT N,
160 PRINT USING "##.###"; U;
170 PRINT " V"
180 NEXT N
190 FOR T= 1 TO 10000 : NEXT T
200 LOCATE 10,1
210 GOTO 120
500 REM ************* Ansteuerung des MAX186 ******
510 CMD = 128 + 16 * SEL + 8 + 4 + 2
520 BIT = 128
530 FOR B= 1 TO 8
540 IF (CMD AND BIT)=BIT THEN RTS = 2 ELSE RTS=0
550 OUT (BA+4),RTS
560 OUT (BA+4),RTS+1
570 OUT (BA+4),RTS
580 BIT = BIT \ 2
590 NEXT B
595 OUT (BA+4),0
600 FOR T= 1 TO 10 : NEXT T
610 BIT = 2048 : AUS = 0
630 FOR B= 1 TO 16
640 OUT (BA+4),1
650 OUT (BA+4),0
660 IF ((INP(BA+6) AND 16)=16) THEN AUS = AUS + BIT
670 BIT = BIT \ 2
680 NEXT B
690 U = AUS / 1000
700 RETURN

can you help me?


TAS2005
At least on the computers I have tried SetcommState is unable to set bits to 8 when stopbits are set to 1 and returns 0 (failed). However 8,0 seems to work in place of 8,1 for the equipment I am communicating with.

SetCommState and result analysis code below.

;kernel32.decls file
.lib "kernel32.dll"
api_CreateFile%(lpFileName$, dwDesiredAccess, dwShareMode, lpSecurrityAttributes*, dwCreationDistribution, dwFlagsAndAttributes, hTemplateFile) : "CreateFileA"
api_SetupComm%(hFile, dwInQueue, dwOutQueue) : "SetupComm"
api_GetCommState%(hFile, lpDCB*) : "GetCommState"
api_SetCommState%(hFile, lpCDB*) : "SetCommState"
api_SetCommMask%(hFile, dwEvtMask) : "SetCommMask"
api_CloseHandle%(hObject) : "CloseHandle"
api_EscapeCommFunction%(hFile, dwFunc) : "EscapeCommFunction"
api_WriteFile%(hFile, lpBuffer*, nNumberOfBytesToWrite, lpNumberOfBytesWritten*, lpOverlapped) : "WriteFile"
api_SetCommTimeouts%(hFile, lpCommTimeouts*) : "SetCommTimeouts"
api_ClearCommError%(hFile, lpErrors*, lpStat*) : "ClearCommError"
api_ReadFile%(hFile, lpBuffer*, nNumberOfBytesToRead, lpNumberOfBytesRead*, lpOverlapped) : "ReadFile"


;Code *********************

dcb = CreateBank(28)
driverHandle = api_CreateFile("COM1", $80000000 Or $40000000 , 0, dcb, 3, 0, 0)
If driverHandle = -1 Then Notify "CreateFile failed" :End

If Not api_SetupComm(driverHandle, 1024, 1024) Then Notify "SetupComm failed": End

PokeInt dcb, 00, 28 ; sizeof(DCB)
PokeInt dcb, 04, 9600 ; baud rate
PokeByte dcb, 08, 1 ; Binary Mode (skip Eof check)
PokeByte dcb, 09, 0 ; No flow control
PokeShort dcb, 14, 2048 ; Xon default
PokeShort dcb, 16, 512 ; XOff default
PokeByte dcb, 18, 8 ; number of bits per byte, 4-8
PokeByte dcb, 19, 0 ; Parity 0-4=no, odd, even, mark, space
PokeByte dcb, 20, 0 ; StopBits 0,1,2 = 1, 1.5, 2
PokeByte dcb, 21, 17 ; Xon Char default
PokeByte dcb, 22, 19 ; Xoff Char default
; 8 bits/byte and 1 stopbit fails!!
; 8 And 0 OK
; 6 And 2 OK
; 7 and 2 OK

r=api_SetCommState(driverHandle, dcb )

; Get the Comm state
For i=0 To 28-1
PokeByte dcb,i,0
Next
PokeInt dcb, 0, 28 ; sizeof(DCB)
api_GetCommState(driverHandle,dcb)

If r=1 Then
;short report
mx$= "SetCommState Suceed!"+Chr$(13)
mx$=mx$+ "handle = "+driverhandle +Chr$(13)
mx$=mx$+ "Baudrate " +PeekInt(dcb,4) +Chr$(13)
mx$=mx$+ "Databits " +PeekByte(dcb,18) +Chr$(13)
mx$=mx$+ "Parity " +PeekByte(dcb,19) +Chr$(13)
mx$=mx$+ "Stopbits " +PeekByte(dcb,20) +Chr$(13)
Notify mx$
Else
;detailed report
Print "SetCommState failed!!"
Print ""
Print "DCB size "+PeekInt(dcb,0)
Print "Baudrate "+PeekInt(dcb,4)
Print "Bit Fields 0-7 "+Right$(Bin(PeekInt(dcb,8)),8)
Print "Bit Fields 8-15 "+Right$(Bin(PeekInt(dcb,8)/256),8)
Print "Res "+PeekShort(dcb,12)
Print "Xon "+PeekShort(dcb,14)
Print "Xoff "+PeekShort(dcb,16)
Print "Bits "+PeekByte(dcb,18)
Print "Parity "+PeekByte(dcb,19)
Print "Stop Bit "+PeekByte(dcb,20)
Print "Char "+PeekByte(dcb,21)
Print "Char "+PeekByte(dcb,22)
Print "Char "+PeekByte(dcb,23)
Print "Char "+PeekByte(dcb,24)
Print "Char "+PeekByte(dcb,25)
Print "Res "+PeekShort(dcb,26)
Stop
EndIf

api_CloseHandle(driverHandle)


;Type dcb
;0 DCBlength As Integer
;4 BaudRate As Integer
;8 **fBitFields As Integer**
;12 wReserved As short
;14 XonLim As short
;16 XoffLim As short
;18 ByteSize As Byte
;19 Parity As Byte
;20 StopBits As Byte
;21 XonChar As Byte
;22 XoffChar As Byte
;23 ErrorChar As Byte
;24 EofChar As Byte
;25 EvtChar As Byte
;26 wReserved1 As short 'Reserved
;End Type

; The fourteen actual DCB bit-sized Data fields within the four bytes of fBitFields
; FieldName Bit # Description
; ----------------- ----- ------------------------------
; fBinary 1 1 binary mode, no Eof check
; fParity 2 2 enable parity checking
; fOutxCtsFlow 3 4 CTS output flow control
; fOutxDsrFlow 4 8 DSR output flow control
; fDtrControl 5 16,32 DTR flow control Type (2 bits)
; fDsrSensitivity 7 64 DSR sensitivity
; fTXContinueOnXoff 8 128 XOFF continues Tx
; fOutX 9 1 XON/XOFF out flow control
; fInX 10 2 XON/XOFF in flow control
; fErrorChar 11 4 enable error replacement
; fNull 12 8 enable Null stripping
; fRtsControl 13 16,32 RTS flow control (2 bits)
; fAbortOnError 15 48 abort reads/writes on error
; fDummy2 16 64 reserved


Litobyte2008
typedef struct _DCB {
DWORD DCBlength; /* sizeof(DCB) */
DWORD BaudRate; /* Baudrate at which running */
DWORD fBinary: 1; /* Binary Mode (skip EOF check) */
DWORD fParity: 1; /* Enable parity checking */
DWORD fOutxCtsFlow:1; /* CTS handshaking on output */
DWORD fOutxDsrFlow:1; /* DSR handshaking on output */
DWORD fDtrControl:2; /* DTR Flow control */
DWORD fDsrSensitivity:1; /* DSR Sensitivity */
DWORD fTXContinueOnXoff: 1; /* Continue TX when Xoff sent */
DWORD fOutX: 1; /* Enable output X-ON/X-OFF */
DWORD fInX: 1; /* Enable input X-ON/X-OFF */
DWORD fErrorChar: 1; /* Enable Err Replacement */
DWORD fNull: 1; /* Enable Null stripping */
DWORD fRtsControl:2; /* Rts Flow control */
DWORD fAbortOnError:1; /* Abort all reads and writes on Error */
DWORD fDummy2:17; /* Reserved */
WORD wReserved; /* Not currently used */
WORD XonLim; /* Transmit X-ON threshold */
WORD XoffLim; /* Transmit X-OFF threshold */
BYTE ByteSize; /* Number of bits/byte, 4-8 */
BYTE Parity; /* 0-4=None,Odd,Even,Mark,Space */
BYTE StopBits; /* 0,1,2 = 1, 1.5, 2 */
char XonChar; /* Tx and Rx X-ON character */
char XoffChar; /* Tx and Rx X-OFF character */
char ErrorChar; /* Error replacement char */
char EofChar; /* End of Input character */
char EvtChar; /* Received Event character */
WORD wReserved1; /* Fill for now. */
} DCB, *LPDCB;


skidracer2009
please see this Archive for more recent code


Code Archives Forum