To LUGNET HomepageTo LUGNET News HomepageTo LUGNET Guide Homepage
 Help on Searching
 
Post new message to lugnet.robotics.rcx.legosOpen lugnet.robotics.rcx.legos in your NNTP NewsreaderTo LUGNET News Traffic PageSign In (Members)
 Robotics / RCX / legOS / 1320
1319  |  1321
Subject: 
Re: solaris + legOS
Newsgroups: 
lugnet.robotics.rcx.legos
Date: 
Fri, 28 Jul 2000 16:03:35 GMT
Viewed: 
4098 times
  
Hi,

Can you send me the full loader.c and any other changes that was done to
get it to compile under Solaris?  I am in the process of re-writing most
of dll to be easier to read (getting rid of a lot of the ifdefs,
renaming functions, etc), but still maintaining the cross-platform
compiling for both UNIX and Windows. Thanks

Ram

Ryan VanderBijl wrote:
> 
> YEAH! It works! And there was great rejoicing! :-)
> 
> This version sucsefully d/led the helloworld.lx, and it ran perfectly.
> Thank you much!
> 
> I'm curious, what all did you change? I saw you did a cool thing to make
> the getopt_long work...  (btw, it gave a small warning saying that
> option_index
> was unused in the main function.)
> That should be applied to convert.c also, although you may have to do
> something with optind to make it work.
> 
> Thanks again!
> 
> Ryan
> 
> > > ... well.. i know that... i tried using that one before.  Like you said,
> > > it
> > > doesn't work.
> > 
> > Could you please try the appended version of loader.c?
> > 
> > Eddie C. Dost
> > ecd@skynet.be
> > --
> > 
> > /*! \file   loader.c
> >     \brief  legOS task downloading
> >     \author Markus L. Noga <markus@noga.de>
> > */
> > 
> > /*
> >  *  The contents of this file are subject to the Mozilla Public License
> >  *  Version 1.0 (the "License"); you may not use this file except in
> >  *  compliance with the License. You may obtain a copy of the License at
> >  *  http://www.mozilla.org/MPL/
> >  *
> >  *  Software distributed under the License is distributed on an "AS IS"
> >  *  basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
> >  *  License for the specific language governing rights and limitations
> >  *  under the License.
> >  *
> >  *  The Original Code is legOS code, released October 2, 1999.
> >  *
> >  *  The Initial Developer of the Original Code is Markus L. Noga.
> >  *  Portions created by Markus L. Noga are Copyright (C) 1999
> >  *  Markus L. Noga. All Rights Reserved.
> >  *
> >  *  Contributor(s): everyone discussing LNP at LUGNET
> >  */
> > 
> > /*  2000.05.01
> >  *
> >  *  Modifications to the original loader.c file for LegOS 0.2.2 include:
> >  *
> >  *  Paolo Masetti's patches to eliminate "Invalid Argument" error and
> >  *  to get rid of several compiler warnings:
> >  *     <paolo.masetti@itlug.org>
> >  *     http://www.lugnet.com/robotics/rcx/legos/?n=619
> >  *
> >  *  Markus L. Noga's solution to Cygwin's failure to define the O_ASYNC
> >  symbol:
> >  *     <markus@noga.de>
> >  *     http://www.lugnet.com/robotics/rcx/legos/?n=439
> >  *
> >  *  Paolo Masetti's adaptation for definitive porting to Win32. No more
> >  errors in
> >  *  serial communication and conditional compile for Winnt (cygnwin).
> >  *  Several addition to dll option to better support user. Execute dll
> >  without
> >  *  arguments to get help.
> >  *     <paolo.masetti@itlug.org>
> >  */
> > 
> > #include <stdio.h>
> > #include <stdlib.h>
> > #include <unistd.h>
> > #include <string.h>
> > #include <fcntl.h>
> > #include <sys/time.h>
> > #include <sys/types.h>
> > #include <signal.h>
> > #include <errno.h>
> > 
> > #if defined(_WIN32)
> >   #include <windows.h>
> > #endif
> > 
> > #include <sys/lnp.h>
> > #include <sys/lnp-logical.h>
> > 
> > #include "rcxtty.h"
> > #include "keepalive.h"
> > #include <lx.h>
> > 
> > #define MAX_DATA_CHUNK 0xf8     //!< maximum data bytes/packet for
> > boot protocol
> > #define XMIT_RETRIES   5        //!< number of packet transmit retries
> > #define REPLY_TIMEOUT  750000   //!< timeout for reply
> > #define BYTE_TIME      (1000*LNP_BYTE_TIME) //!< time to transmit a byte.
> > 
> > #define DEFAULT_DEST  0
> > #define DEFAULT_PROGRAM 0
> > #define DEFAULT_SRCPORT 0
> > #define DEFAULT_PRIORITY 10
> > 
> > typedef enum {
> >   CMDacknowledge,     //!< 1:
> >   CMDdelete,       //!< 1+ 1: b[nr]
> >   CMDcreate,       //!< 1+12: b[nr] s[textsize] s[datasize] s[bsssize] s[stacksize] s[start] b[prio]
> >   CMDoffsets,       //!< 1+ 7: b[nr] s[text] s[data] s[bss]
> >   CMDdata,         //!< 1+>3: b[nr] s[offset] array[data]
> >   CMDrun,           //!< 1+ 1: b[nr]
> >   CMDirmode, //!< 1+ 1: b[0=near/1=far]
> >   CMDlast           //!< ?
> > } packet_cmd_t;
> > 
> > #if defined(__sun__) && defined(__svr4__)
> > #define _SOLARIS 1
> > #endif
> > 
> > #if !defined(_SOLARIS)
> > #include <getopt.h>
> > 
> > static const struct option long_options[]={
> >   {"rcxaddr",required_argument,0,'r'},
> >   {"program",required_argument,0,'p'},
> >   {"srcport",required_argument,0,'s'},
> >   {"tty",    required_argument,0,'t'},
> >   {"irmode", required_argument,0,'i'},
> >   {"execute",no_argument      ,0,'e'},
> >   {"verbose",no_argument      ,0,'v'},
> >   {0        ,0                ,0,0  }
> > };
> > 
> > #else // _SOLARIS
> > 
> > #define getopt_long(ac, av, opt, lopt, lidx) (getopt((ac), (av), (opt)))
> > 
> > #endif // _SOLARIS
> > 
> > volatile int receivedAck=0;
> > 
> > volatile unsigned short relocate_to=0;
> > 
> > unsigned int  rcxaddr = DEFAULT_DEST,
> >               prog    = DEFAULT_PROGRAM,
> >               srcport = DEFAULT_SRCPORT,
> >    irmode  = -1;
> > 
> > int run_flag=0;
> > int verbose_flag=0;
> > 
> > void io_handler(void);
> > 
> > /*! blocking I/R write.
> >  *! return number of bytes written, or negative for error.
> >  */
> > int lnp_logical_write(const void *data, size_t length) {
> > 
> > // With Win32 we are using Blocking Write by default
> > #if !defined(_WIN32)
> >   fd_set fds;
> > 
> >   // wait for transmission
> >   //
> >   do {
> >     FD_ZERO(&fds);
> >     FD_SET(rcxFD(),&fds);
> >   } while(select(rcxFD()+1,NULL,&fds,NULL,NULL)<1);
> > #endif
> > 
> >   // transmit
> >   //
> >   keepaliveRenew();
> > 
> >   return mywrite(rcxFD(), data, length)!=length;
> > }
> > 
> > //! send a LNP layer 0 packet of given length
> > /*! \return 0 on success.
> > */
> > int lnp_assured_write(const unsigned char *data, unsigned char length,
> >                       unsigned char dest, unsigned char srcport) {
> >   int i;
> >   struct timeval timeout,now;
> >   unsigned long total,elapsed;
> > 
> >   for(i=0; i<XMIT_RETRIES; i++) {
> >     receivedAck=0;
> > 
> >     lnp_addressing_write(data,length,dest,srcport);
> > 
> >     gettimeofday(&timeout,0);
> >     total=REPLY_TIMEOUT+length*BYTE_TIME;
> >     elapsed=0;
> > 
> >     do {
> > #if defined(_WIN32)
> >       io_handler();
> > #else
> >       struct timeval tv;
> >       fd_set fds;
> > 
> >       FD_ZERO(&fds);
> >       FD_SET(rcxFD(), &fds);
> > 
> >       tv.tv_sec = (total - elapsed) / 1000000;
> >       tv.tv_usec = (total - elapsed) % 1000000;
> >       select(rcxFD() + 1, &fds, NULL, NULL, &tv);
> >       if (FD_ISSET(rcxFD(), &fds))
> >  io_handler();
> > #endif
> > 
> >       gettimeofday(&now,0);
> >       elapsed=1000000*(now.tv_sec  - timeout.tv_sec ) +
> >                now.tv_usec - timeout.tv_usec;
> > 
> >     } while((!receivedAck) && (elapsed < total));
> > 
> >     if(i || !receivedAck)
> >       if(verbose_flag)
> >         fprintf(stderr,"try %d: ack:%d\n",i,receivedAck);
> > 
> >     if(receivedAck)
> >       return 0;
> >    }
> > 
> >   return -1;
> > }
> > 
> > void io_handler(void) {
> > 
> >     static struct timeval last={0,0};
> >     struct timeval now;
> >     unsigned long diff;
> > 
> >     unsigned char buffer[256];
> > #if defined(_WIN32)
> >     DWORD len;
> >     int i;
> > #else
> >     int len,i;
> > #endif
> > 
> >     gettimeofday(&now,0);
> >     diff= 1000000*now .tv_sec + now .tv_usec -
> >  (1000000*last.tv_sec + last.tv_usec);
> > 
> >     if(diff> 10000*LNP_BYTE_TIMEOUT) {
> >       if(verbose_flag)
> >         fprintf(stderr,"\n#time %lu ",diff);
> >       lnp_integrity_reset();
> >     }
> > #if defined(_WIN32)
> >     ReadFile(rcxFD(), buffer, sizeof(buffer), &len, NULL);
> > #else
> >     len=read(rcxFD(),buffer,sizeof(buffer));
> > #endif
> >     for(i=0; i<len; i++) {
> >       if(verbose_flag)
> >         fprintf(stderr,"%02x ",buffer[i]);
> >       lnp_integrity_byte(buffer[i]);
> >     }
> >     gettimeofday(&last,0);
> > }
> > 
> > void LNPinit(const char *tty) {
> >   struct timeval timeout,now;
> >   long diff;
> > 
> > #if !defined(_WIN32)
> >   unsigned char buffer[256];
> > #endif
> > 
> >   // initialize RCX communications
> >   //
> >   if (verbose_flag) fputs("opening tty...\n", stderr);
> > #ifdef LNP_FAST
> >   rcxInit(tty, 1);
> > #else
> >   rcxInit(tty, 0);
> > #endif
> > 
> >   if (rcxFD() == BADFILE) {
> >     myperror("opening tty");
> >     exit(1);
> >   }
> >   keepaliveInit();
> > 
> >   // wait for IR to settle
> >   //
> >   gettimeofday(&timeout,0);
> >   do {
> >     usleep(100000);
> >     gettimeofday(&now,0);
> >     diff=1000000*(now.tv_sec  - timeout.tv_sec ) +
> >            now.tv_usec - timeout.tv_usec;
> > 
> >   } while(diff < 100000);
> > #if defined(_WIN32)
> >   PurgeComm(rcxFD(), PURGE_TXABORT | PURGE_RXABORT | PURGE_TXCLEAR | PURGE_RXCLEAR);
> > #else
> >   read(rcxFD(),buffer,256);
> > #endif
> > }
> > 
> > void ahandler(const unsigned char *data,unsigned char len,unsigned char src)
> > {
> >   if(*data==CMDacknowledge) {
> >     receivedAck=1;
> >     if(len==8) {
> >       // offset packet
> >       //
> >       relocate_to=(data[2]<<8)|data[3];
> >     }
> >   }
> > }
> > 
> > void lnp_download(const lx_t *lx) {
> >   unsigned char buffer[256+3];
> > 
> >   size_t i,chunkSize,totalSize=lx->text_size+lx->data_size;
> > 
> >   if(verbose_flag)
> >     fputs("\ndata ",stderr);
> > 
> >   buffer[0]=CMDdata;
> >   buffer[1]=prog;
> > 
> >   for(i=0; i<totalSize; i+=chunkSize) {
> >     chunkSize=totalSize-i;
> >     if(chunkSize>MAX_DATA_CHUNK)
> >       chunkSize=MAX_DATA_CHUNK;
> > 
> >     buffer[2]= i >> 8;
> >     buffer[3]= i &  0xff;
> >     memcpy(buffer+4,lx->text + i,chunkSize);
> >     if(lnp_assured_write(buffer,chunkSize+4,rcxaddr,srcport)) {
> >       fputs("error downloading program\n",stderr);
> >       exit(-1);
> >     }
> >   }
> > }
> > 
> > int main(int argc, char **argv) {
> >   lx_t lx;        // the legOS executable
> >   char *filename;
> >   int opt,option_index;
> > 
> >   unsigned char buffer[256+3]="";
> >   char *tty=NULL;
> > 
> >   while((opt=getopt_long(argc, argv, "r:p:s:t:i:ev",
> >                         (struct option *)long_options, &option_index) )!=-1)
> >                         {
> >     switch(opt) {
> >       case 'e':
> >    run_flag=1;
> >         break;
> >       case 'r':
> >    sscanf(optarg,"%x",&rcxaddr);
> >         break;
> >       case 'p':
> >    sscanf(optarg,"%x",&prog);
> >         break;
> >       case 's':
> >    sscanf(optarg,"%x",&srcport);
> >         break;
> >       case 't':
> >    sscanf(optarg,"%s",buffer);
> >         break;
> >       case 'i':
> >    sscanf(optarg,"%x",&irmode);
> >         break;
> >       case 'v':
> >    verbose_flag=1;
> >    break;
> >     }
> >   }
> > 
> >   // load executable
> >   //
> >   if(argc-optind<1) {
> >     char *usage_string =
> >  "  -p<prognum>  , --program=<prognum>   set destination program to <prognum>\n"
> >  "  -r<rcxadress>, --rcxaddr=<rcxadress> set RCX address to <rcxaddress>\n"
> >  "  -s<srcadress>, --srcport=<srcadress> set RCX sourceport to
> > <srcaddress>\n"
> >  "  -t<comport>  , --tty=<comport>       set IR Tower com port <comport>\n"
> >  "  -i<0/1>      , --irmode=<0/1>        set IR mode near(0)/far(1) on
> > RCX\n"
> >  "  -e           , --execute             execute program after download\n"
> >  "  -v           , --verbose             verbose mode\n"
> >  "\n"
> >  "Default com port can be set using environment variable RCXTTY.\n"
> >  "Eg:\tset RCXTTY=COM2\n"
> >  "\n"
> >  ;
> > 
> >  fprintf(stderr, "usage: %s [options] file.lx\n", argv[0]);
> >  fprintf(stderr, usage_string);
> > 
> >     return -1;
> >   }
> >   filename=argv[optind++];
> >   if(lx_read(&lx,filename)) {
> >     fprintf(stderr,"unable to load legOS executable from %s.\n",filename);
> >     return -1;
> >   }
> > 
> >   // Moved tty device setting for a new option on command line
> >   if (buffer[0]) tty=buffer;
> >   if (!tty) tty = getenv(TTY_VARIABLE);
> >   if (!tty) tty = DEFAULTTTY;
> > 
> >   LNPinit(tty);
> > 
> >   if (verbose_flag)
> >     fputs("\nLNP Initialized...\n",stderr);
> > 
> >   lnp_addressing_set_handler(0,ahandler);
> > 
> >   if(verbose_flag)
> >     fprintf(stderr,"loader hostaddr=%02x hostmask=%02x portmask=%02x\n",
> >             LNP_HOSTADDR & 0x00ff,LNP_HOSTMASK & 0x00ff, LNP_PORTMASK &
> >             0x00ff);
> > 
> >   // Set IR mode
> >   if (irmode != -1) {
> >     buffer[0]=CMDirmode;
> >     buffer[1]=irmode;
> >     if(lnp_assured_write(buffer,2,rcxaddr,srcport)) {
> >       fputs("error setting IR mode to far\n",stderr);
> >       return -1;
> >     }
> >   }
> > 
> >   if(verbose_flag)
> >     fputs("\ndelete",stderr);
> >   buffer[0]=CMDdelete;
> >   buffer[1]=prog; //       prog 0
> >   if(lnp_assured_write(buffer,2,rcxaddr,srcport)) {
> >     fputs("error deleting program\n",stderr);
> >     return -1;
> >   }
> > 
> >   if(verbose_flag)
> >     fputs("\ncreate ",stderr);
> >   buffer[ 0]=CMDcreate;
> >   buffer[ 1]=prog; //       prog 0
> >   buffer[ 2]=lx.text_size>>8;
> >   buffer[ 3]=lx.text_size & 0xff;
> >   buffer[ 4]=lx.data_size>>8;
> >   buffer[ 5]=lx.data_size & 0xff;
> >   buffer[ 6]=lx.bss_size>>8;
> >   buffer[ 7]=lx.bss_size & 0xff;
> >   buffer[ 8]=lx.stack_size>>8;
> >   buffer[ 9]=lx.stack_size & 0xff;
> >   buffer[10]=lx.offset >> 8;  // start offset from text segment
> >   buffer[11]=lx.offset & 0xff;
> >   buffer[12]=DEFAULT_PRIORITY;
> >   if(lnp_assured_write(buffer,13,rcxaddr,srcport)) {
> >     fputs("error creating program\n",stderr);
> >     return -1;
> >   }
> > 
> >   // relocation target address in relocate_to
> >   //
> >   lx_relocate(&lx,relocate_to);
> > 
> >   lnp_download(&lx);
> > 
> >   if (run_flag) {
> >     if(verbose_flag)
> >       fputs("\nrun ",stderr);
> >     buffer[0]=CMDrun;
> >     buffer[1]=prog; //       prog 0
> >     if(lnp_assured_write(buffer,2,rcxaddr,srcport)) {
> >       fputs("error running program\n",stderr);
> >       return -1;
> >     }
> >   }
> > 
> >   return 0;
> > }
> 
> 
> --
> Ryan VanderBijl                        http://www.calvin.edu/~rvbijl39
> 
> (Frodo:) "I don't want to answer a string of questions while I am
> eating. I want to think!" "Good heavens!" said Pippin. "At breakfast?"
> 
> 



Message has 1 Reply:
  Re: solaris + legOS
 
(...) Actually you should refer to CVS files that are available from (URL) tree contains the Solaris patch too. Bye, Paolo. --- Gambling: The sure way of getting nothing for something. (26 years ago, 1-Aug-00, to lugnet.robotics.rcx.legos)

Message is in Reply To:
  Re: solaris + legOS
 
YEAH! It works! And there was great rejoicing! :-) This version sucsefully d/led the helloworld.lx, and it ran perfectly. Thank you much! I'm curious, what all did you change? I saw you did a cool thing to make the getopt_long work... (btw, it gave (...) (26 years ago, 28-Jul-00, to lugnet.robotics.rcx.legos)

3 Messages in This Thread:

Entire Thread on One Page:
Nested:  All | Brief | Compact | Dots
Linear:  All | Brief | Compact

This Message and its Replies on One Page:
Nested:  All | Brief | Compact | Dots
Linear:  All | Brief | Compact
    

©2005 LUGNET. All rights reserved. - hosted by steinbruch.info GbR