The code below is from a project I have worked on that uses the RS485
on the SER4 boards. You need to write to a register on the PLD and
then toggle the RTS line to control Rx & Tx.
Regards,
Clive
static int Serial_Open(PDCH handle)
{
....
#if defined( LINUX_ARM )
/*
* The ARM boards require a register setting for the RS485 to work
*
* It would be nice to have this automatically done by the PLD,
but for
* now we need to write directly to the I/O registers.
*
* Thank you Andrew Bealing for the help here!
*
*/
if ( ci->u.Serial.fRS485 )
{
int memfd;
volatile unsigned char *io;
unsigned char io_byte;
Debug(3, Fmt("RS485 enabled, trying to set TS-SER4 RS485
enable bit.\n"));
/*
* Open a memory handle
*/
memfd = open("/dev/mem", O_RDWR);
if ( memfd < 0 )
{
Debug(1, Fmt("E0457: Unable to access memory handle to
enable RS485 option!\n"));
gLastErrCode = _ERR_DC_SERIAL_DEVICE_;
return gLastErrCode;
}
/*
* Map to the actual I/O location
*/
io = (unsigned char *)mmap(0, getpagesize(),
PROT_READ | PROT_WRITE, MAP_SHARED, memfd, _PCI_IO_BASE_);
if ( ! io )
{
Debug(1, Fmt("E0457: Unable to access memory to enable
RS485 option!\n"));
gLastErrCode = _ERR_DC_SERIAL_DEVICE_;
return gLastErrCode;
}
io += _SER_IO_BOARD_BASE_[ci->u.Serial.nBoard] + 3; /* RS485
option register */
io_byte = *io;
*io = io_byte | 0x80; /* set bit 7 to enable RS485 */
Debug(3, Fmt("RS485 option enabled.\n"));
}
#endif
}
static int Serial_Send_Handler(PDCH handle, PDC_PACKET pDCPacket)
{
....
{
#if 1
/*
* Before writing we must assert RTS
*/
if( ioctl(ci->u.Serial.fd, TIOCMBIS, &aMCR) == -1)
Debug(2, Fmt("WARNING: ioctl(..) was unable to set RTS!\n"));
#endif
numOfBytesWrite = write(ci->u.Serial.fd, handle->PT->Tx.packet,
handle->PT->Tx.len);
#if 1
/*
* Now wait until all the bytes have gone
*/
nTimeout = 100;
while( nTimeout-- )
{
if(ioctl(ci->u.Serial.fd, TIOCSERGETLSR, &aLSR) == -1)
{
Debug(2, "WARNING: ioctl(..) failed to get LSR!\n");
break;
}
if( aLSR ) /* is the TSR empty? */
break;
msleep(100);
}
if ( ! nTimeout )
Debug(2, "WARNING: ioctl(..) timeout waiting for TSR to empty!\n");
/*
* We have finished, so clear RTS
*/
if( ioctl(ci->u.Serial.fd, TIOCMBIC, &aMCR) == -1)
Debug(2, Fmt("WARNING: ioctl(..) was unable to clr RTS!\n"));
#endif
--- In "Yan Seiner" <> wrote:
>
> I am trying to get RS485 running on one of the expansion card ports.
> I have the 4 port serial card. My RS485 device is hooked up to COM C,
> which has the RS485 option enabled ( the jumper is on.)
>
> When I try to turn on RS485 using
>
> if(proto == RS485HD) {
> int mcr, ret;
> mcr = AUTO485HD;
> //mcr = AUTO485FD //for full duplex
> ret = ioctl (fd, TIOC_SBCS485, &mcr);
> if(Mb_verbose)
> printf("setting RS parameters returned %d: fd: %d, request: %d,
> value: %d\n",ret, fd, TIOC_SBCS485, mcr);
> }
>
> I always get back a -1 status, meaning that the ioctl call failed.
>
> setting ok:
> device /dev/ttyS2
> speed 9600
> data bits 8
> stop bits 1
> parity 0
> ioctl failed: Invalid argument
> setting RS parameters returned -1: fd: 3, request: 1074025585, value: 4
>
> I can't figure out why this is failing.... Anyone have RS485 running
> on the expansion card? Could someone shed some light on this?
>
> Thanks,
>
> --Yan
>
------------------------ Yahoo! Groups Sponsor --------------------~-->
Most low income households are not online. Help bridge the digital divide today!
http://us.click.yahoo.com/cd_AJB/QnQLAA/TtwFAA/CFFolB/TM
--------------------------------------------------------------------~->
Yahoo! Groups Links
<*> To visit your group on the web, go to:
http://groups.yahoo.com/group/ts-7000/
<*> To unsubscribe from this group, send an email to:
<*> Your use of Yahoo! Groups is subject to:
http://docs.yahoo.com/info/terms/
|