Newsgroup: it.comp.lang.visual-basic
Titolo: Problemi con ReadFileEx() e porte seriali

Ciao a tutti,
sto sviluppando un software che deve comunicare con certi dispositivi
connessi
alle porte seriali (oppure attraverso TCP/IP oppure modem, ecc.)
Ho pensato di utilizzare la ReadFileEx() per vari motivi ma non ci sono
riuscito.
Apro la seriale con CreateFile specificando FILE_FLAG_OVERLAPPED e
GENERIC_READ,
uso ReadFileEx() per ricevere i byte. L'errore deriva dal fatto che la
ReadFileEX()
ritorna 0 (errore) e GetLastError() ritorna 6, INVALID_HANDLE_VALUE. Ma la
CreateFile()
crea un handle valido.
Più o meno il codice è il seguente:
 Dim handle As Long
 Dim d As DCB
 Dim data(10) As Byte
 Dim strOverlpd As OVERLAPPED
 Dim rxData(10) As Byte
        hFile = CreateFile("COM1", _
            GENERIC_WRITE Or GENERIC_READ, _
            0, 0, OPEN_EXISTING, FILE_FLAG_OVERLAPPED, 0)
        If hFile = INVALID_HANDLE_VALUE Then
            MsgBox "Error opening COM1", vbOKOnly
            Exit Sub
        End If
        lRet = BuildCommDCB("baud=19200 parity=N data=8 stop=1", d)
        If SetCommState(hFile, d) = 0 Then
            'Errore
            MsgBox "Error setting COM1 parameters", vbOKOnly
            Exit Sub
        End If
        ' Setta i timeout della seriale
        cto.ReadIntervalTimeout = 0
        cto.ReadTotalTimeoutConstant = TIMEOUT_CONSTANT
        cto.ReadTotalTimeoutMultiplier = TIMEOUT_MULTIPLIER
        If SetCommTimeouts(handle, cto) = 0 Then
            MsgBox "Error setting COM1 parameters", vbOKOnly
            Exit Sub
        End If
     Call PurgeComm(hFile, PURGE_RXCLEAR)
     ReDim RxData(EKAComm.nrBytesToReceived)
     lRet = ReadFileEx(hFile, RxData(0), 10, strOverlpd, AddressOf
RxCallback)
     If lRet = 0 Then
         lRet = GetLastError()
         MsgBox lRet   ' Error INVALID_HANDLE_VALUE
     End If
Le dichiarazioni usate sono:
Global Const GENERIC_READ = &H80000000
Global Const GENERIC_WRITE = &H40000000
Global Const OPEN_EXISTING = 3
Global Const FILE_FLAG_OVERLAPPED = &H40000000
Global Const INVALID_HANDLE_VALUE = -1
Global Const PURGE_RXCLEAR = &H8     '  Annulla il buffer di prescrittura se
esiste.
Global Const ERROR_IO_PENDING = 997 '  dderror
Public Type DCB
        DCBlength As Long
        BaudRate As Long
        fBinary As Long
        fParity As Long
        fOutxCtsFlow As Long
        fOutxDsrFlow As Long
        fDtrControl As Long
        fDsrSensitivity As Long
        fTXContinueOnXoff As Long
        fOutX As Long
        fInX As Long
        fErrorChar As Long
        fNull As Long
        fRtsControl As Long
        fAbortOnError As Long
        fDummy2 As Long
        wReserved As Integer
        XonLim As Integer
        XoffLim As Integer
        ByteSize As Byte
        Parity As Byte
        StopBits As Byte
        XonChar As Byte
        XoffChar As Byte
        ErrorChar As Byte
        EofChar As Byte
        EvtChar As Byte
End Type
Public Type OVERLAPPED
        Internal As Long
        InternalHigh As Long
        offset As Long
        OffsetHigh As Long
        hEvent As Long
End Type
Public Declare Function BuildCommDCB Lib "kernel32" Alias "BuildCommDCBA"
(ByVal _
        lpDef As String, lpDCB _
        As DCB) As Long
Public Declare Function CreateFile Lib "kernel32" Alias "CreateFileA" ( _
        ByVal lpFileName As String, _
        ByVal dwDesiredAccess As Long, _
        ByVal dwShareMode As Long, _
        ByVal lpSecurityAttributes As Long, _
        ByVal dwCreationDisposition As Long, _
        ByVal dwFlagsAndAttributes As Long, _
        ByVal hTemplateFile As Long) As Long
Public Declare Function SetCommState Lib "kernel32" ( _
        ByVal hCommDev As Long, _
        lpDCB As DCB) As Long
Public Declare Function SetCommTimeouts Lib "kernel32" ( _
        ByVal hFile As Long, _
        lpCommTimeouts As COMMTIMEOUTS) As Long
Public Declare Function CloseHandle Lib "kernel32" ( _
        ByVal hObject As Long) As Long
Public Declare Function PurgeComm Lib "kernel32" ( _
        ByVal hFile As Long, _
        ByVal dwFlags As Long) As Long
Public Declare Function CreateEvent Lib "kernel32" Alias "CreateEventA" ( _
        ByVal lpEventAttributes As Long, _
        ByVal bManualReset As Long, _
        ByVal bInitialState As Long, _
        ByVal lpName As String) As Long
Public Declare Function WriteFile Lib "kernel32" ( _
        ByVal hFile As Long, _
        lpBuffer As Any, _
        ByVal nNumberOfBytesToWrite As Long, _
        lpNumberOfBytesWritten As Long, _
        lpOverlapped As OVERLAPPED) As Long
Public Declare Function ReadFileEx Lib "kernel32" ( _
        ByVal hFile As Long, _
        lpBuffer As Any, _
        ByVal nNumberOfBytesToRead As Long, _
        lpOverlapped As OVERLAPPED, _
        ByVal lpCompletionRoutine As Long) As Long

La struttura DBC è sicuramente superata, leggiti quella nuova
(e i commenti) in win32api2.txt.
il resto "potrebbe" andare bene.
Carlo

 il resto "potrebbe" andare bene.
Fatto, ma non cambia nulla. :(