linux-decnet-commit Mailing List for DECnet for Linux (Page 37)
Brought to you by:
chrissie_c,
ph3-der-loewe
You can subscribe to this list here.
2001 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
(15) |
Nov
(16) |
Dec
(6) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2002 |
Jan
(20) |
Feb
(27) |
Mar
(25) |
Apr
(12) |
May
(2) |
Jun
(6) |
Jul
(36) |
Aug
(12) |
Sep
(12) |
Oct
(16) |
Nov
(5) |
Dec
(5) |
2003 |
Jan
(8) |
Feb
(9) |
Mar
(25) |
Apr
(18) |
May
(29) |
Jun
(4) |
Jul
(1) |
Aug
|
Sep
(10) |
Oct
(5) |
Nov
(3) |
Dec
(9) |
2004 |
Jan
(17) |
Feb
|
Mar
(9) |
Apr
|
May
(4) |
Jun
(1) |
Jul
(2) |
Aug
(21) |
Sep
|
Oct
|
Nov
|
Dec
(1) |
2005 |
Jan
(5) |
Feb
|
Mar
(13) |
Apr
|
May
(3) |
Jun
(1) |
Jul
|
Aug
|
Sep
(13) |
Oct
(83) |
Nov
(2) |
Dec
|
2006 |
Jan
(21) |
Feb
(1) |
Mar
(32) |
Apr
(31) |
May
(3) |
Jun
(1) |
Jul
|
Aug
(7) |
Sep
|
Oct
(1) |
Nov
(3) |
Dec
(13) |
2007 |
Jan
(1) |
Feb
(7) |
Mar
|
Apr
(2) |
May
|
Jun
(1) |
Jul
(2) |
Aug
(20) |
Sep
|
Oct
|
Nov
|
Dec
(7) |
2008 |
Jan
(4) |
Feb
(13) |
Mar
(24) |
Apr
(18) |
May
(10) |
Jun
|
Jul
|
Aug
(40) |
Sep
(72) |
Oct
(61) |
Nov
(9) |
Dec
(2) |
2009 |
Jan
(6) |
Feb
(1) |
Mar
|
Apr
|
May
|
Jun
(7) |
Jul
|
Aug
|
Sep
|
Oct
(8) |
Nov
|
Dec
(3) |
2010 |
Jan
|
Feb
|
Mar
|
Apr
(5) |
May
|
Jun
|
Jul
(41) |
Aug
(28) |
Sep
(2) |
Oct
(5) |
Nov
(4) |
Dec
|
2011 |
Jan
(7) |
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
From: Patrick C. <pa...@us...> - 2002-07-10 09:33:46
|
Update of /cvsroot/linux-decnet/dnprogs In directory usw-pr-cvs1:/tmp/cvs-serv16020 Modified Files: TODO Log Message: Stuff done and todo. Index: TODO =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/TODO,v retrieving revision 1.5 retrieving revision 1.6 diff -C2 -r1.5 -r1.6 *** TODO 2 Jun 2001 17:12:09 -0000 1.5 --- TODO 10 Jul 2002 09:33:43 -0000 1.6 *************** *** 4,7 **** --- 4,8 ---- fal Reports of problems with FAL on DECnet/E. I'm sending too many ACKS again. + Also odd problems on RSX11M, maybe the same. phone: *************** *** 10,16 **** command line. Only happens rarely (to me!) ! ctermd: ! DEL key not recognised. ! In fact line-editting doesn't work at all. This is quite a large problem ! ...I need volunteers for this. ! --- 11,15 ---- command line. Only happens rarely (to me!) ! sethost ! line-editting needs adding - rewrite as dnlogin started. ! problem with sethost->VMS then set host to VMS again. maybe echo troubles |
From: Patrick C. <pa...@us...> - 2002-07-10 07:45:27
|
Update of /cvsroot/linux-decnet/dnprogs/fal In directory usw-pr-cvs1:/tmp/cvs-serv5437 Modified Files: directory.cc Log Message: Hack for RSX directory listings. Index: directory.cc =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/fal/directory.cc,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -r1.4 -r1.5 *** directory.cc 10 Jul 2002 07:11:46 -0000 1.4 --- directory.cc 10 Jul 2002 07:45:24 -0000 1.5 *************** *** 1,4 **** /****************************************************************************** ! (c) 1998-2000 P.J. Caulfield pa...@ty... This program is free software; you can redistribute it and/or modify --- 1,4 ---- /****************************************************************************** ! (c) 1998-2002 P.J. Caulfield pa...@ty... This program is free software; you can redistribute it and/or modify *************** *** 85,90 **** dap_access_message *am = (dap_access_message *)m; - strcpy(filespec, am->get_filespec()); split_filespec(volume, directory, filespec); --- 85,97 ---- dap_access_message *am = (dap_access_message *)m; strcpy(filespec, am->get_filespec()); + + // If we are talking to RSX and it did not send a filespec + // then default to *.* + if (params.remote_os == 4 && filespec[0] == '\0') + { + strcpy(filespec, "*.*"); + } + split_filespec(volume, directory, filespec); |
From: Patrick C. <pa...@us...> - 2002-07-10 07:39:24
|
Update of /cvsroot/linux-decnet/dnprogs/libdaemon In directory usw-pr-cvs1:/tmp/cvs-serv2526 Modified Files: dnet_daemon.c Log Message: Ignore blank lines Index: dnet_daemon.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/libdaemon/dnet_daemon.c,v retrieving revision 1.9 retrieving revision 1.10 diff -C2 -r1.9 -r1.10 *** dnet_daemon.c 10 Jul 2002 06:56:32 -0000 1.9 --- dnet_daemon.c 10 Jul 2002 07:39:21 -0000 1.10 *************** *** 152,156 **** while (*bufp == ' ' || *bufp == '\t') bufp++; ! if (*bufp == '#') continue; // Comment // Remove trailing LF --- 152,156 ---- while (*bufp == ' ' || *bufp == '\t') bufp++; ! if (*bufp == '#' || *bufp == '\n') continue; // Comment or blank line // Remove trailing LF |
From: Patrick C. <pa...@us...> - 2002-07-10 07:11:49
|
Update of /cvsroot/linux-decnet/dnprogs/fal In directory usw-pr-cvs1:/tmp/cvs-serv24565/fal Modified Files: directory.cc open.cc task.cc Log Message: Lower-case filenames when talking to RSX remove some trailing spaces. Index: directory.cc =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/fal/directory.cc,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -r1.3 -r1.4 *** directory.cc 26 Sep 2001 09:01:06 -0000 1.3 --- directory.cc 10 Jul 2002 07:11:46 -0000 1.4 *************** *** 334,338 **** st.set_errno(); st.write(conn); ! } return true; } --- 334,338 ---- st.set_errno(); st.write(conn); ! } return true; } Index: open.cc =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/fal/open.cc,v retrieving revision 1.9 retrieving revision 1.10 diff -C2 -r1.9 -r1.10 *** open.cc 16 Oct 2001 12:24:53 -0000 1.9 --- open.cc 10 Jul 2002 07:11:46 -0000 1.10 *************** *** 1,5 **** /****************************************************************************** (c) 1998-2000 P.J. Caulfield pa...@ty... ! This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by --- 1,5 ---- /****************************************************************************** (c) 1998-2000 P.J. Caulfield pa...@ty... ! This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by *************** *** 97,103 **** if (verbose > 1) DAPLOG((LOG_DEBUG, "fal_open: ACCESS message:\n")); ! dap_access_message *am = (dap_access_message *)m; ! // Get the filespec and split it into bits strcpy(filespec, am->get_filespec()); --- 97,103 ---- if (verbose > 1) DAPLOG((LOG_DEBUG, "fal_open: ACCESS message:\n")); ! dap_access_message *am = (dap_access_message *)m; ! // Get the filespec and split it into bits strcpy(filespec, am->get_filespec()); *************** *** 117,121 **** write_access=true; } ! // Convert % wildcards to ? if (vms_format) convert_vms_wildcards(filespec); --- 117,121 ---- write_access=true; } ! // Convert % wildcards to ? if (vms_format) convert_vms_wildcards(filespec); *************** *** 158,173 **** // Send whatever attributes were requested; ! // Only send the DEV field if the target file is // one we can handle natively because // DEV (as a disk device) makes VMS send files in block mode. ! if (verbose > 1) DAPLOG((LOG_INFO, "org = %d, rfm = %d\n", ! attrib_msg->get_org(), attrib_msg->get_rfm())); if (!create) { ! if (!send_file_attributes(block_size, use_records, gl.gl_pathv[glob_entry], ! am->get_display(), DEV_DEPENDS_ON_TYPE)) { --- 158,173 ---- // Send whatever attributes were requested; ! // Only send the DEV field if the target file is // one we can handle natively because // DEV (as a disk device) makes VMS send files in block mode. ! if (verbose > 1) DAPLOG((LOG_INFO, "org = %d, rfm = %d\n", ! attrib_msg->get_org(), attrib_msg->get_rfm())); if (!create) { ! if (!send_file_attributes(block_size, use_records, gl.gl_pathv[glob_entry], ! am->get_display(), DEV_DEPENDS_ON_TYPE)) { *************** *** 178,184 **** else { ! if (!send_file_attributes(block_size, use_records, gl.gl_pathv[glob_entry], ! am->get_display(), DONT_SEND_DEV)) { --- 178,184 ---- else { ! if (!send_file_attributes(block_size, use_records, gl.gl_pathv[glob_entry], ! am->get_display(), DONT_SEND_DEV)) { *************** *** 254,258 **** { case dap_accomp_message::END_OF_STREAM: ! // write metafile if (params.use_metafiles && create) --- 254,258 ---- { case dap_accomp_message::END_OF_STREAM: ! // write metafile if (params.use_metafiles && create) *************** *** 274,278 **** if (record_lengths) delete[] record_lengths; ! if (!send_file_attributes(block_size, use_records, gl.gl_pathv[glob_entry], display, SEND_DEV)) return false; --- 274,278 ---- if (record_lengths) delete[] record_lengths; ! if (!send_file_attributes(block_size, use_records, gl.gl_pathv[glob_entry], display, SEND_DEV)) return false; *************** *** 289,297 **** // finished task if (stream) ! { fclose(stream); stream = NULL; } ! // Do close options if (am->get_fop_bit(dap_attrib_message::FB$SPL) || --- 289,297 ---- // finished task if (stream) ! { fclose(stream); stream = NULL; } ! // Do close options if (am->get_fop_bit(dap_attrib_message::FB$SPL) || *************** *** 332,336 **** { dap_status_message *sm = (dap_status_message *)m; ! if (sm->get_code() & 0x0FFF != 0x10) { --- 332,336 ---- { dap_status_message *sm = (dap_status_message *)m; ! if (sm->get_code() & 0x0FFF != 0x10) { *************** *** 344,348 **** default: ! DAPLOG((LOG_WARNING, "unexpected message type %d received\n", m->get_type() )); return false; --- 344,348 ---- default: ! DAPLOG((LOG_WARNING, "unexpected message type %d received\n", m->get_type() )); return false; *************** *** 376,380 **** // if not then we block data & status message. Ether way we enable // blocking here. ! conn.set_blocked(true); // Seek to VBN or RFA (VBNs start at one) --- 376,380 ---- // if not then we block data & status message. Ether way we enable // blocking here. ! conn.set_blocked(true); // Seek to VBN or RFA (VBNs start at one) *************** *** 401,405 **** if (::fread(buf, 1, record_lengths[current_record], stream) < 1) ateof = true; ! // We read a whole record (including our "compatibility" LF) // which VMS does not want. --- 401,405 ---- if (::fread(buf, 1, record_lengths[current_record], stream) < 1) ateof = true; ! // We read a whole record (including our "compatibility" LF) // which VMS does not want. *************** *** 417,421 **** int newchar; buflen = 0; ! do { newchar = getc(stream); --- 417,421 ---- int newchar; buflen = 0; ! do { newchar = getc(stream); *************** *** 435,439 **** buflen=bs; } ! // We got some data if (!ateof) --- 435,439 ---- buflen=bs; } ! // We got some data if (!ateof) *************** *** 480,484 **** am.set_cmpfunc(dap_accomp_message::RESPONSE); am.write(conn); ! conn.set_blocked(false); return false; } --- 480,484 ---- am.set_cmpfunc(dap_accomp_message::RESPONSE); am.write(conn); ! conn.set_blocked(false); return false; } *************** *** 499,508 **** { dap_status_message status; ! status.set_code(010225); // Operation successful DAPLOG((LOG_DEBUG, "Sending RFA of %d\n", record_pos )); status.set_rfa( record_pos ); status.write(conn); ! conn.set_blocked(false); } return true; --- 499,508 ---- { dap_status_message status; ! status.set_code(010225); // Operation successful DAPLOG((LOG_DEBUG, "Sending RFA of %d\n", record_pos )); status.set_rfa( record_pos ); status.write(conn); ! conn.set_blocked(false); } return true; *************** *** 525,547 **** datalen -= attrib_msg->get_fsz(); } ! // FORTRAN files: First byte indicates carriage control if (attrib_msg->get_rat_bit(dap_attrib_message::FB$FTN)) { ! switch (dataptr[0]) { case '+': // No new line dataptr[0] = '\r'; break; ! case '1': // Form Feed dataptr[0] = '\f'; break; ! case '0': // Two new lines dataptr[0] = '\n'; if (!fwrite("\n", 1, 1, stream)) return false; break; ! case ' ': // new line --- 525,547 ---- datalen -= attrib_msg->get_fsz(); } ! // FORTRAN files: First byte indicates carriage control if (attrib_msg->get_rat_bit(dap_attrib_message::FB$FTN)) { ! switch (dataptr[0]) { case '+': // No new line dataptr[0] = '\r'; break; ! case '1': // Form Feed dataptr[0] = '\f'; break; ! case '0': // Two new lines dataptr[0] = '\n'; if (!fwrite("\n", 1, 1, stream)) return false; break; ! case ' ': // new line *************** *** 598,602 **** sprintf(cmd, PRINT_COMMAND, gl.gl_pathv[glob_entry]); ! int status = system(cmd); --- 598,602 ---- sprintf(cmd, PRINT_COMMAND, gl.gl_pathv[glob_entry]); ! int status = system(cmd); *************** *** 625,629 **** DAPLOG((LOG_DEBUG, "fal_open: CONTROL: type %d, rac=%x\n", cm->get_ctlfunc(), cm->get_rac() )); ! // Determine whether to enable streaming or not int access_mode = cm->get_rac(); --- 625,629 ---- DAPLOG((LOG_DEBUG, "fal_open: CONTROL: type %d, rac=%x\n", cm->get_ctlfunc(), cm->get_rac() )); ! // Determine whether to enable streaming or not int access_mode = cm->get_rac(); *************** *** 653,660 **** { dap_status_message status; ! status.set_code(010047); // EOF status.write(conn); ! conn.set_blocked(false); } --- 653,660 ---- { dap_status_message status; ! status.set_code(010047); // EOF status.write(conn); ! conn.set_blocked(false); } *************** *** 695,699 **** stream = fdopen(fd, "w+"); ! if (!stream) { close(fd); --- 695,699 ---- stream = fdopen(fd, "w+"); ! if (!stream) { close(fd); Index: task.cc =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/fal/task.cc,v retrieving revision 1.7 retrieving revision 1.8 diff -C2 -r1.7 -r1.8 *** task.cc 9 Dec 2001 16:30:12 -0000 1.7 --- task.cc 10 Jul 2002 07:11:46 -0000 1.8 *************** *** 1,5 **** /****************************************************************************** (c) 1998-2000 P.J. Caulfield pa...@ty... ! This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by --- 1,5 ---- /****************************************************************************** (c) 1998-2000 P.J. Caulfield pa...@ty... ! This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by *************** *** 15,19 **** // task.cc // Base class for a task within a FAL server process. ! // All real tasks subclass this but we provide here some basic services such // as filename conversion and parsing that they all need. #include <sys/types.h> --- 15,19 ---- // task.cc // Base class for a task within a FAL server process. ! // All real tasks subclass this but we provide here some basic services such // as filename conversion and parsing that they all need. #include <sys/types.h> *************** *** 55,59 **** void fal_task::return_error(int code) { ! if (verbose > 1) DAPLOG((LOG_ERR, "fal_task error: %s\n", strerror(code))); --- 55,59 ---- void fal_task::return_error(int code) { ! if (verbose > 1) DAPLOG((LOG_ERR, "fal_task error: %s\n", strerror(code))); *************** *** 91,96 **** // Splits a filename up into volume, directory and file parts. // The volume and directory are just for display purposes (they get sent back ! // to the client). file is the (possibly) wildcard filespec to use for ! // searching for files. // // Unix filenames are just returned as-is. --- 91,96 ---- // Splits a filename up into volume, directory and file parts. // The volume and directory are just for display purposes (they get sent back ! // to the client). file is the (possibly) wildcard filespec to use for ! // searching for files. // // Unix filenames are just returned as-is. *************** *** 101,104 **** --- 101,110 ---- void fal_task::split_filespec(char *volume, char *directory, char *file) { + // If the remote client is RSX then lower-case the filename + if (params.remote_os == 4) + { + dap_connection::makelower(file); + } + if (is_vms_name(file)) { *************** *** 151,155 **** char *lastslash; struct stat st; ! // Resolve all relative bits and symbolic links realpath(unixname, fullname); --- 157,161 ---- char *lastslash; struct stat st; ! // Resolve all relative bits and symbolic links realpath(unixname, fullname); *************** *** 163,167 **** if (!strchr(lastslash, '.')) strcat(fullname, "."); ! // If it's a directory then add .DIR;1 if (lstat(unixname, &st)==0 && S_ISDIR(st.st_mode)) --- 169,173 ---- if (!strchr(lastslash, '.')) strcat(fullname, "."); ! // If it's a directory then add .DIR;1 if (lstat(unixname, &st)==0 && S_ISDIR(st.st_mode)) *************** *** 170,174 **** if (fullname[strlen(fullname)-1] != '.') strcat(fullname, "."); ! strcat(fullname, "DIR;1"); // last dot has already been added } --- 176,180 ---- if (fullname[strlen(fullname)-1] != '.') strcat(fullname, "."); ! strcat(fullname, "DIR;1"); // last dot has already been added } *************** *** 200,204 **** int slashes = 0; ! // Oh, also make it all upper case for VMS's benefit. for (i=0; i<(int)strlen(fullname); i++) --- 206,210 ---- int slashes = 0; ! // Oh, also make it all upper case for VMS's benefit. for (i=0; i<(int)strlen(fullname); i++) *************** *** 210,214 **** } } ! // File is in the root directory if (slashes == 1) --- 216,220 ---- } } ! // File is in the root directory if (slashes == 1) *************** *** 277,281 **** *ptr = saved; } ! char *enddir = strchr(ptr, ']'); if (*ptr == '[' && enddir) // we have a directory --- 283,287 ---- *ptr = saved; } ! char *enddir = strchr(ptr, ']'); if (*ptr == '[' && enddir) // we have a directory *************** *** 288,296 **** *ptr = saved; } ! // Copy the rest of the filename using memmove 'cos it might overlap if (ptr != file) memmove(file, ptr, strlen(ptr)+1); ! } --- 294,302 ---- *ptr = saved; } ! // Copy the rest of the filename using memmove 'cos it might overlap if (ptr != file) memmove(file, ptr, strlen(ptr)+1); ! } *************** *** 315,319 **** if (file[strlen(file)-1] == '.') file[strlen(file)-1] = '\0'; ! unixname[0] = '\0'; --- 321,325 ---- if (file[strlen(file)-1] == '.') file[strlen(file)-1] = '\0'; ! unixname[0] = '\0'; *************** *** 324,328 **** if (volume[strlen(volume)-1] == ':') volume[strlen(volume)-1] = '\0'; ! // If the filename has the dummy SYSDISK volume then start from the // filesystem root --- 330,334 ---- if (volume[strlen(volume)-1] == ':') volume[strlen(volume)-1] = '\0'; ! // If the filename has the dummy SYSDISK volume then start from the // filesystem root *************** *** 340,344 **** } ptr = strlen(unixname); ! // Copy the directory for (i=0; i< (int)strlen(dir); i++) --- 346,350 ---- } ptr = strlen(unixname); ! // Copy the directory for (i=0; i< (int)strlen(dir); i++) *************** *** 428,432 **** // // Most of the subclasses use these routines to send the file attributes in ! // response to an ACCESS message. // The option to send the DEV field is really for CREATE because when VMS // sees the block device it tries to send the file in block mode and we then --- 434,438 ---- // // Most of the subclasses use these routines to send the file attributes in ! // response to an ACCESS message. // The option to send the DEV field is really for CREATE because when VMS // sees the block device it tries to send the file in block mode and we then *************** *** 441,448 **** ! bool fal_task::send_file_attributes(unsigned int &block_size, bool &use_records, ! char *filename, ! int display, dev_option show_dev) { --- 447,454 ---- ! bool fal_task::send_file_attributes(unsigned int &block_size, bool &use_records, ! char *filename, ! int display, dev_option show_dev) { *************** *** 479,486 **** // There's hardly anything in this message but it keeps VMS quiet ! if (display & dap_access_message::DISPLAY_ALLOC_MASK) { dap_alloc_message alloc_msg; ! if (!alloc_msg.write(conn)) return false; } --- 485,492 ---- // There's hardly anything in this message but it keeps VMS quiet ! if (display & dap_access_message::DISPLAY_ALLOC_MASK) { dap_alloc_message alloc_msg; ! if (!alloc_msg.write(conn)) return false; } *************** *** 490,494 **** { dap_date_message date_msg; ! date_msg.set_cdt(st.st_ctime); date_msg.set_rdt(st.st_mtime); --- 496,500 ---- { dap_date_message date_msg; ! date_msg.set_cdt(st.st_ctime); date_msg.set_rdt(st.st_mtime); *************** *** 496,505 **** if (!date_msg.write(conn)) return false; } ! // Send the protection if (display & dap_access_message::DISPLAY_PROT_MASK) { dap_protect_message prot_msg; ! prot_msg.set_protection(st.st_mode); prot_msg.set_owner(st.st_gid, st.st_uid); --- 502,511 ---- if (!date_msg.write(conn)) return false; } ! // Send the protection if (display & dap_access_message::DISPLAY_PROT_MASK) { dap_protect_message prot_msg; ! prot_msg.set_protection(st.st_mode); prot_msg.set_owner(st.st_gid, st.st_uid); *************** *** 511,519 **** { dap_name_message name_msg; ! if (vms_format) { char vmsname[PATH_MAX]; ! make_vms_filespec(filename, vmsname, true); name_msg.set_namespec(vmsname); --- 517,525 ---- { dap_name_message name_msg; ! if (vms_format) { char vmsname[PATH_MAX]; ! make_vms_filespec(filename, vmsname, true); name_msg.set_namespec(vmsname); *************** *** 574,580 **** // Guess file type ! if (params.auto_type == fal_params::GUESS_TYPE) return guess_file_type(blocksize, send_records, name, attrib_msg); ! if (params.auto_type == fal_params::CHECK_EXT) return check_file_type(blocksize, send_records, name, attrib_msg); --- 580,586 ---- // Guess file type ! if (params.auto_type == fal_params::GUESS_TYPE) return guess_file_type(blocksize, send_records, name, attrib_msg); ! if (params.auto_type == fal_params::CHECK_EXT) return check_file_type(blocksize, send_records, name, attrib_msg); *************** *** 584,588 **** // Guess the file type based on the first few bytes and set the attrib // message ! bool fal_task::guess_file_type(unsigned int &block_size, bool &send_records, const char *name, dap_attrib_message *attrib_msg) { --- 590,594 ---- // Guess the file type based on the first few bytes and set the attrib // message ! bool fal_task::guess_file_type(unsigned int &block_size, bool &send_records, const char *name, dap_attrib_message *attrib_msg) { *************** *** 758,762 **** strncpy(num, fileptr, numlen); num[numlen] = '\0'; ! block_size = atoi(num); } --- 764,768 ---- strncpy(num, fileptr, numlen); num[numlen] = '\0'; ! block_size = atoi(num); } *************** *** 764,768 **** auto_types *new_type = new auto_types(extension, use_records, block_size); if (verbose > 2) ! DAPLOG((LOG_DEBUG, "Type: %s, %c, %d\n", extension, use_records?'r':'b', block_size)); --- 770,774 ---- auto_types *new_type = new auto_types(extension, use_records, block_size); if (verbose > 2) ! DAPLOG((LOG_DEBUG, "Type: %s, %c, %d\n", extension, use_records?'r':'b', block_size)); *************** *** 862,866 **** // Read file metadata - return true if it exists, false otherwise ! bool fal_task::read_metafile(unsigned int &block_size, bool &send_records, const char *name, dap_attrib_message *attrib_msg) { --- 868,872 ---- // Read file metadata - return true if it exists, false otherwise ! bool fal_task::read_metafile(unsigned int &block_size, bool &send_records, const char *name, dap_attrib_message *attrib_msg) { *************** *** 917,921 **** // For variable-length records we always send as records if we // need to consult the metadata. ! if (metadata.rfm & dap_attrib_message::FB$VAR && record_lengths != NULL) { --- 923,927 ---- // For variable-length records we always send as records if we // need to consult the metadata. ! if (metadata.rfm & dap_attrib_message::FB$VAR && record_lengths != NULL) { *************** *** 957,967 **** metadata.version = metafile_data::METAFILE_VERSION; metadata.num_records = current_record; ! // Calculate Longest Record Length. unsigned int lrl = 0; for (unsigned int i=0; i<current_record; i++) if (record_lengths[i] > lrl) lrl = record_lengths[i]; ! ! // Our record lengths include the terminating LF so // subtract that from the length. // If there are no records then put MRS in there. --- 963,973 ---- metadata.version = metafile_data::METAFILE_VERSION; metadata.num_records = current_record; ! // Calculate Longest Record Length. unsigned int lrl = 0; for (unsigned int i=0; i<current_record; i++) if (record_lengths[i] > lrl) lrl = record_lengths[i]; ! ! // Our record lengths include the terminating LF so // subtract that from the length. // If there are no records then put MRS in there. *************** *** 985,989 **** // Read VMS NFS "ADF" file - return true if it exists, false otherwise ! bool fal_task::read_adf(unsigned int &block_size, bool &send_records, const char *name, dap_attrib_message *attrib_msg) { --- 991,995 ---- // Read VMS NFS "ADF" file - return true if it exists, false otherwise ! bool fal_task::read_adf(unsigned int &block_size, bool &send_records, const char *name, dap_attrib_message *attrib_msg) { *************** *** 1004,1008 **** } fclose(adf); ! adfs.rfm = adfs.rfm & 0xF; attrib_msg->set_rfm(adfs.rfm); --- 1010,1014 ---- } fclose(adf); ! adfs.rfm = adfs.rfm & 0xF; attrib_msg->set_rfm(adfs.rfm); |
From: Patrick C. <pa...@us...> - 2002-07-10 06:56:36
|
Update of /cvsroot/linux-decnet/dnprogs/libdaemon In directory usw-pr-cvs1:/tmp/cvs-serv20208 Modified Files: dnet_daemon.c Log Message: If the password fails to match then convert it to all lower-case and try again. This is for RSX's benefit as it sends all upper-cased passwords. Index: dnet_daemon.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/libdaemon/dnet_daemon.c,v retrieving revision 1.8 retrieving revision 1.9 diff -C2 -r1.8 -r1.9 *** dnet_daemon.c 28 Jan 2001 17:27:36 -0000 1.8 --- dnet_daemon.c 10 Jul 2002 06:56:32 -0000 1.9 *************** *** 99,105 **** // Make sure we reap all children ! do ! { ! pid = waitpid(-1, &status, WNOHANG); if (pid > 0 && verbose) DNETLOG((LOG_INFO, "Reaped child process %d\n", pid)); } --- 99,105 ---- // Make sure we reap all children ! do ! { ! pid = waitpid(-1, &status, WNOHANG); if (pid > 0 && verbose) DNETLOG((LOG_INFO, "Reaped child process %d\n", pid)); } *************** *** 137,141 **** DNETLOG((LOG_ERR, "Can't open proxy database: %s\n", strerror(errno))); return; ! } line = 0; --- 137,141 ---- DNETLOG((LOG_ERR, "Can't open proxy database: %s\n", strerror(errno))); return; ! } line = 0; *************** *** 145,149 **** char *bufp = buf; char *colons; ! line++; if (!fgets(buf, sizeof(buf), f)) break; --- 145,149 ---- char *bufp = buf; char *colons; ! line++; if (!fgets(buf, sizeof(buf), f)) break; *************** *** 156,160 **** // Remove trailing LF if (buf[strlen(buf)-1] == '\n') buf[strlen(buf)-1] = '\0'; ! colons = strstr(bufp, "::"); if (colons) --- 156,160 ---- // Remove trailing LF if (buf[strlen(buf)-1] == '\n') buf[strlen(buf)-1] = '\0'; ! colons = strstr(bufp, "::"); if (colons) *************** *** 164,168 **** char *end; char *local; ! if (!space) space = strchr(colons, '\t'); if (!space) --- 164,168 ---- char *end; char *local; ! if (!space) space = strchr(colons, '\t'); if (!space) *************** *** 274,284 **** // Check the proxy database for authentication ! static bool check_proxy_database(char *nodename, ! char *remoteuser, char *localuser) { bool found = FALSE; struct proxy *p; ! // Re-read the proxy database 'cos it has changed. free_proxy(); --- 274,284 ---- // Check the proxy database for authentication ! static bool check_proxy_database(char *nodename, ! char *remoteuser, char *localuser) { bool found = FALSE; struct proxy *p; ! // Re-read the proxy database 'cos it has changed. free_proxy(); *************** *** 309,313 **** } ! // // Wait for an incoming connection // Returns a new fd or -1 --- 309,313 ---- } ! // // Wait for an incoming connection // Returns a new fd or -1 *************** *** 319,323 **** struct sockaddr_dn sockaddr; static bool listening = FALSE; ! memset(&sockaddr, 0, sizeof(sockaddr)); --- 319,323 ---- struct sockaddr_dn sockaddr; static bool listening = FALSE; ! memset(&sockaddr, 0, sizeof(sockaddr)); *************** *** 378,382 **** int have_shadow = -1; memset(&sockaddr, 0, sizeof(sockaddr)); ! // Get the name (or address if we cant find the name) of the remote system. // (a) for logging and (b) for checking in the proxy database. --- 378,382 ---- int have_shadow = -1; memset(&sockaddr, 0, sizeof(sockaddr)); ! // Get the name (or address if we cant find the name) of the remote system. // (a) for logging and (b) for checking in the proxy database. *************** *** 389,398 **** else { ! snprintf(nodename, sizeof(nodename), "%d.%d", (sockaddr.sdn_add.a_addr[1] >> 2), (((sockaddr.sdn_add.a_addr[1] & 0x03) << 8) | sockaddr.sdn_add.a_addr[0])); } ! // Only do this if we are dnetd if (object_db) --- 389,398 ---- else { ! snprintf(nodename, sizeof(nodename), "%d.%d", (sockaddr.sdn_add.a_addr[1] >> 2), (((sockaddr.sdn_add.a_addr[1] & 0x03) << 8) | sockaddr.sdn_add.a_addr[0])); } ! // Only do this if we are dnetd if (object_db) *************** *** 420,424 **** // Get the remote user spec. if (getsockopt(sockfd, DNPROTO_NSP, SO_CONACCESS, &accessdata, ! &len) < 0) { snprintf(errstring, sizeof(errstring), --- 420,424 ---- // Get the remote user spec. if (getsockopt(sockfd, DNPROTO_NSP, SO_CONACCESS, &accessdata, ! &len) < 0) { snprintf(errstring, sizeof(errstring), *************** *** 446,459 **** ! if (verbose) { if (username[0]) { ! DNETLOG((LOG_DEBUG, "Connection from: %s\"%s password\"::%s\n", nodename, username, remote_user)); } else { ! DNETLOG((LOG_DEBUG, "Connection from: %s::%s\n", nodename, remote_user)); } --- 446,459 ---- ! if (verbose) { if (username[0]) { ! DNETLOG((LOG_DEBUG, "Connection from: %s\"%s password\"::%s\n", nodename, username, remote_user)); } else { ! DNETLOG((LOG_DEBUG, "Connection from: %s::%s\n", nodename, remote_user)); } *************** *** 529,533 **** { snprintf(errstring, sizeof(errstring), ! "Error reading /etc/shadow entry for %s: %s", username, strerror(errno)); lasterror=errstring; --- 529,533 ---- { snprintf(errstring, sizeof(errstring), ! "Error reading /etc/shadow entry for %s: %s", username, strerror(errno)); lasterror=errstring; *************** *** 537,550 **** } endspent(); // prevent caching of passwords ! ! // Check the shadow password cryptpass = crypt(password, spw->sp_pwdp); if (strcmp(cryptpass, spw->sp_pwdp)) { ! snprintf(errstring, sizeof(errstring), ! "Incorrect password for %s", username); ! lasterror=errstring; ! dnet_reject(sockfd, DNSTAT_ACCCONTROL, NULL, 0); ! return -1; } } --- 537,557 ---- } endspent(); // prevent caching of passwords ! ! // Check the shadow password cryptpass = crypt(password, spw->sp_pwdp); if (strcmp(cryptpass, spw->sp_pwdp)) { ! // If that failed then lower-case the password and try again. ! // This is really for RSX which sends the password in all caps ! makelower(password); ! cryptpass = crypt(password, spw->sp_pwdp); ! if (strcmp(cryptpass, spw->sp_pwdp)) ! { ! snprintf(errstring, sizeof(errstring), ! "Incorrect password for %s", username); ! lasterror=errstring; ! dnet_reject(sockfd, DNSTAT_ACCCONTROL, NULL, 0); ! return -1; ! } } } *************** *** 552,569 **** #endif { ! // Check the (non-shadow) password cryptpass = crypt(password, pw->pw_passwd); if (strcmp(cryptpass, pw->pw_passwd)) { ! snprintf(errstring, sizeof(errstring), ! "Incorrect password for %s", username); ! lasterror=errstring; ! dnet_reject(sockfd, DNSTAT_ACCCONTROL, NULL, 0); ! return -1; } } } ! // NO_FORK is just for testing. It creates a single-shot server that is // easier to debug. #ifdef NO_FORK --- 559,582 ---- #endif { ! // Check the (non-shadow) password cryptpass = crypt(password, pw->pw_passwd); if (strcmp(cryptpass, pw->pw_passwd)) { ! // Check lower-case password as above. ! makelower(password); ! cryptpass = crypt(password, pw->pw_passwd); ! if (strcmp(cryptpass, pw->pw_passwd)) ! { ! snprintf(errstring, sizeof(errstring), ! "Incorrect password for %s", username); ! lasterror=errstring; ! dnet_reject(sockfd, DNSTAT_ACCCONTROL, NULL, 0); ! return -1; ! } } } } ! // NO_FORK is just for testing. It creates a single-shot server that is // easier to debug. #ifdef NO_FORK *************** *** 622,629 **** if (!f) { ! DNETLOG((LOG_ERR, "Can't open dnetd.conf database: %s\n", strerror(errno))); return; ! } line = 0; --- 635,642 ---- if (!f) { ! DNETLOG((LOG_ERR, "Can't open dnetd.conf database: %s\n", strerror(errno))); return; ! } line = 0; *************** *** 636,640 **** struct object *newobj; int state = 1; ! line++; if (!fgets(buf, sizeof(buf), f)) break; --- 649,653 ---- struct object *newobj; int state = 1; ! line++; if (!fgets(buf, sizeof(buf), f)) break; *************** *** 654,658 **** if (*bufp == '\0') continue; // Empty line ! // Split into fields newobj = malloc(sizeof(struct object)); --- 667,671 ---- if (*bufp == '\0') continue; // Empty line ! // Split into fields newobj = malloc(sizeof(struct object)); *************** *** 727,731 **** bind_sockaddr.sdn_objnamel = 0; ! status = bind(sockfd, (struct sockaddr *)&bind_sockaddr, sizeof(bind_sockaddr)); if (status) --- 740,744 ---- bind_sockaddr.sdn_objnamel = 0; ! status = bind(sockfd, (struct sockaddr *)&bind_sockaddr, sizeof(bind_sockaddr)); if (status) *************** *** 744,748 **** struct sockaddr_dn bind_sockaddr; int status; ! memset(&bind_sockaddr, 0, sizeof(bind_sockaddr)); bind_sockaddr.sdn_family = AF_DECnet; --- 757,761 ---- struct sockaddr_dn bind_sockaddr; int status; ! memset(&bind_sockaddr, 0, sizeof(bind_sockaddr)); bind_sockaddr.sdn_family = AF_DECnet; *************** *** 752,756 **** strcpy(bind_sockaddr.sdn_objname, object); ! status = bind(sockfd, (struct sockaddr *)&bind_sockaddr, sizeof(bind_sockaddr)); if (status) --- 765,769 ---- strcpy(bind_sockaddr.sdn_objname, object); ! status = bind(sockfd, (struct sockaddr *)&bind_sockaddr, sizeof(bind_sockaddr)); if (status) *************** *** 769,773 **** struct sockaddr_dn bind_sockaddr; int status; ! memset(&bind_sockaddr, 0, sizeof(bind_sockaddr)); bind_sockaddr.sdn_family = AF_DECnet; --- 782,786 ---- struct sockaddr_dn bind_sockaddr; int status; ! memset(&bind_sockaddr, 0, sizeof(bind_sockaddr)); bind_sockaddr.sdn_family = AF_DECnet; *************** *** 776,780 **** bind_sockaddr.sdn_objnamel = 0; ! status = bind(sockfd, (struct sockaddr *)&bind_sockaddr, sizeof(bind_sockaddr)); if (status) --- 789,793 ---- bind_sockaddr.sdn_objnamel = 0; ! status = bind(sockfd, (struct sockaddr *)&bind_sockaddr, sizeof(bind_sockaddr)); if (status) *************** *** 792,801 **** // just return 0 (stdin's file descriptor). otherwise we // bind to the object and wait. When we get a connection we fork ! // and (optionally) setuid, and return. The parent then loops back (ie it // never returns). ! // // This is the keystone of all DECnet daemons that can be called from dnetd // ! int dnet_daemon(int object, char *named_object, int verbosity, bool do_fork) { --- 805,814 ---- // just return 0 (stdin's file descriptor). otherwise we // bind to the object and wait. When we get a connection we fork ! // and (optionally) setuid, and return. The parent then loops back (ie it // never returns). ! // // This is the keystone of all DECnet daemons that can be called from dnetd // ! int dnet_daemon(int object, char *named_object, int verbosity, bool do_fork) { *************** *** 811,815 **** memset(&sa, 0, sizeof(sa)); ! // Are we the execed child of dnetd? if (getsockname(STDIN_FILENO, (struct sockaddr *)&sa, &namelen) == 0) --- 824,828 ---- memset(&sa, 0, sizeof(sa)); ! // Are we the execed child of dnetd? if (getsockname(STDIN_FILENO, (struct sockaddr *)&sa, &namelen) == 0) *************** *** 841,853 **** perror("server: can't fork"); exit(2); ! case 0: // child break; ! default: // Parent. if (verbosity > 1) printf("server: forked process %d\n", pid); ! exit(0); } ! // Detach ourself from the calling environment for (i=0; i<FD_SETSIZE; i++) --- 854,866 ---- perror("server: can't fork"); exit(2); ! case 0: // child break; ! default: // Parent. if (verbosity > 1) printf("server: forked process %d\n", pid); ! exit(0); } ! // Detach ourself from the calling environment for (i=0; i<FD_SETSIZE; i++) *************** *** 869,873 **** siga.sa_flags = 0; sigaction(SIGCHLD, &siga, NULL); ! siga.sa_handler=sigterm; sigaction(SIGTERM, &siga, NULL); --- 882,886 ---- siga.sa_flags = 0; sigaction(SIGCHLD, &siga, NULL); ! siga.sa_handler=sigterm; sigaction(SIGTERM, &siga, NULL); *************** *** 877,881 **** // Create the socket ! if ((sockfd=socket(AF_DECnet,SOCK_SEQPACKET,DNPROTO_NSP)) == -1) { snprintf(errstring, sizeof(errstring), "socket failed: %s", strerror(errno)); --- 890,894 ---- // Create the socket ! if ((sockfd=socket(AF_DECnet,SOCK_SEQPACKET,DNPROTO_NSP)) == -1) { snprintf(errstring, sizeof(errstring), "socket failed: %s", strerror(errno)); *************** *** 887,896 **** setsockopt(sockfd, DNPROTO_NSP, SO_CONDATA, &optdata, sizeof(optdata)); ! #ifdef DSO_ACCEPTMODE acceptmode = ACC_DEFER; setsockopt(sockfd, DNPROTO_NSP, DSO_ACCEPTMODE, &acceptmode, 4); #endif ! // Bind the object if (object) --- 900,909 ---- setsockopt(sockfd, DNPROTO_NSP, SO_CONDATA, &optdata, sizeof(optdata)); ! #ifdef DSO_ACCEPTMODE acceptmode = ACC_DEFER; setsockopt(sockfd, DNPROTO_NSP, DSO_ACCEPTMODE, &acceptmode, 4); #endif ! // Bind the object if (object) *************** *** 902,906 **** if (named_object) bind_status = bind_name(sockfd, named_object); ! else bind_status = bind_wild(sockfd); } --- 915,919 ---- if (named_object) bind_status = bind_name(sockfd, named_object); ! else bind_status = bind_wild(sockfd); } *************** *** 912,916 **** return -1; // Can't bind } ! if (verbose) DNETLOG((LOG_INFO, "Ready\n")); --- 925,929 ---- return -1; // Can't bind } ! if (verbose) DNETLOG((LOG_INFO, "Ready\n")); *************** *** 920,924 **** int fork_fail = 0; int newone; ! // Wait for a new connection. newone = waitfor(sockfd); --- 933,937 ---- int fork_fail = 0; int newone; ! // Wait for a new connection. newone = waitfor(sockfd); *************** *** 934,938 **** exit(100); } ! // Oh no, it all went horribly wrong. DNETLOG((LOG_ERR, "Fork_and_setuid failed: %s\n", lasterror)); --- 947,951 ---- exit(100); } ! // Oh no, it all went horribly wrong. DNETLOG((LOG_ERR, "Fork_and_setuid failed: %s\n", lasterror)); *************** *** 943,947 **** return newone; break; ! default: // parent, just tidy up and loop back fork_fail = 0; --- 956,960 ---- return newone; break; ! default: // parent, just tidy up and loop back fork_fail = 0; *************** *** 965,969 **** optdata.opt_optl=len; if (len && data) memcpy(optdata.opt_data, data, len); ! setsockopt(sockfd, DNPROTO_NSP, DSO_CONDATA, &optdata, sizeof(optdata)); --- 978,982 ---- optdata.opt_optl=len; if (len && data) memcpy(optdata.opt_data, data, len); ! setsockopt(sockfd, DNPROTO_NSP, DSO_CONDATA, &optdata, sizeof(optdata)); |
From: Patrick C. <pa...@us...> - 2002-06-25 07:08:17
|
Update of /cvsroot/linux-decnet/dnprogs/dnlogin In directory usw-pr-cvs1:/tmp/cvs-serv15012 Modified Files: cterm.c dnlogin.c dnlogin.h Log Message: A bit of tidying and some needed prototypes. Index: cterm.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnlogin/cterm.c,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -r1.2 -r1.3 *** cterm.c 18 Jun 2002 19:36:54 -0000 1.2 --- cterm.c 25 Jun 2002 07:08:14 -0000 1.3 *************** *** 59,63 **** 0x02, 0x02, 0xF4, 0x03, /* Max input buf */ 0x03, 0x04, 0xFE, 0x7F, 0x00, /* Supp. Msgs */ ! 0x00}; found_common_write(initsq, sizeof(initsq)); --- 59,64 ---- 0x02, 0x02, 0xF4, 0x03, /* Max input buf */ 0x03, 0x04, 0xFE, 0x7F, 0x00, /* Supp. Msgs */ ! 0x00 ! }; found_common_write(initsq, sizeof(initsq)); *************** *** 131,135 **** /* Process buffer from cterm host */ ! int process_cterm(char *buf, int len) { int offset = 0; --- 132,136 ---- /* Process buffer from cterm host */ ! int cterm_process_network(char *buf, int len) { int offset = 0; *************** *** 195,199 **** ! int cterm_write(char *buf, int len) { char newbuf[len+9]; --- 196,200 ---- ! int cterm_send_input(char *buf, int len, int flags) { char newbuf[len+9]; Index: dnlogin.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnlogin/dnlogin.c,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -r1.2 -r1.3 *** dnlogin.c 18 Jun 2002 19:36:54 -0000 1.2 --- dnlogin.c 25 Jun 2002 07:08:14 -0000 1.3 *************** *** 52,55 **** --- 52,58 ---- static int echo = 1; + /* Output processor */ + int (*send_input)(char *buf, int len, int flags); + /* Raw write to terminal */ int tty_write(char *buf, int len) *************** *** 151,155 **** if (is_terminator(buf[i])) { ! cterm_write(&buf[i], 1); return 0; } --- 154,158 ---- if (is_terminator(buf[i])) { ! send_input(&buf[i], 1, 0); return 0; } *************** *** 159,163 **** if (input_len == max_read_len) { ! cterm_write(input_buf, input_len); } --- 162,166 ---- if (input_len == max_read_len) { ! send_input(input_buf, input_len, 0); } *************** *** 276,280 **** } ! if (found_setup_link(argv[optind], DNOBJECT_CTERM, process_cterm) == 0) { setup_tty("/dev/tty", 1); --- 279,284 ---- } ! send_input = cterm_send_input; ! if (found_setup_link(argv[optind], DNOBJECT_CTERM, cterm_process_network) == 0) { setup_tty("/dev/tty", 1); Index: dnlogin.h =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnlogin/dnlogin.h,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -r1.2 -r1.3 *** dnlogin.h 18 Jun 2002 19:36:54 -0000 1.2 --- dnlogin.h 25 Jun 2002 07:08:14 -0000 1.3 *************** *** 15,18 **** --- 15,19 ---- + /* Foundation services routines */ extern char *found_connerror(char *default_msg); extern int found_getsockfd(void); *************** *** 22,29 **** extern int found_common_write(char *buf, int len); ! extern int process_cterm(char *buf, int len); ! extern int tty_write(char *buf, int len); extern int debug; --- 23,39 ---- extern int found_common_write(char *buf, int len); + /* cterm/dterm routines */ + extern int cterm_send_input(char *buf, int len, int flags); + extern int cterm_process_network(char *buf, int len); ! /* TTY routines */ extern int tty_write(char *buf, int len); + extern void tty_set_terminators(char *buf, int len); + extern void tty_start_read(char *prompt, int len, int promptlen); + extern void tty_set_timeout(unsigned short to); + extern void tty_set_maxlen(unsigned short len); + + + /* Global variables */ extern int debug; |
From: Patrick C. <pa...@us...> - 2002-06-18 19:36:58
|
Update of /cvsroot/linux-decnet/dnprogs/dnlogin In directory usw-pr-cvs1:/tmp/cvs-serv30837 Modified Files: cterm.c dnlogin.c dnlogin.h found.c Log Message: More code. Index: cterm.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnlogin/cterm.c,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** cterm.c 16 Jun 2002 18:45:24 -0000 1.1 --- cterm.c 18 Jun 2002 19:36:54 -0000 1.2 *************** *** 33,37 **** #include "dnlogin.h" ! #define CTERM_MSG_INITIATE 1 #define CTERM_MSG_START_READ 2 --- 33,38 ---- #include "dnlogin.h" ! // We get sent (in order) ! // 11, 7, 2, 7 #define CTERM_MSG_INITIATE 1 #define CTERM_MSG_START_READ 2 *************** *** 50,95 **** /* Process incoming CTERM messages */ ! static int ct_process_initiate(char *buf, int len) { return len; } ! static int ct_process_start_read(char *buf, int len) ! {return len;} ! static int ct_process_read_data(char *buf, int len) ! {return len;} ! static int ct_process_oob(char *buf, int len) {return len;} ! static int ct_process_unread(char *buf, int len) {return len;} ! static int ct_process_clear_input(char *buf, int len) {return len;} ! static int ct_process_write(char *buf, int len) {return len;} ! static int ct_process_write_complete(char *buf, int len) {return len;} ! static int ct_process_discard_state(char *buf, int len) {return len;} ! static int ct_process_read_characteristics(char *buf, int len) {return len;} ! static int ct_process_characteristics(char *buf, int len) {return len;} ! static int ct_process_check_input(char *buf, int len) {return len;} ! static int ct_process_input_count(char *buf, int len) {return len;} ! static int ct_process_input_state(char *buf, int len) {return len;} --- 51,131 ---- /* Process incoming CTERM messages */ ! static int cterm_process_initiate(char *buf, int len) { + unsigned char initsq[] = + { 0x01, 0x00, 0x01, 0x04, 0x00, + 'd', 'n', 'l', 'o', 'g', 'i', 'n', ' ', + 0x01, 0x02, 0x00, 0x02, /* Max msg size */ + 0x02, 0x02, 0xF4, 0x03, /* Max input buf */ + 0x03, 0x04, 0xFE, 0x7F, 0x00, /* Supp. Msgs */ + 0x00}; + + found_common_write(initsq, sizeof(initsq)); return len; } ! static int cterm_process_start_read(char *buf, int len) ! { ! unsigned short flags = buf[1] | buf[2]<<8; ! unsigned short maxlength = buf[3] | buf[4]<<8; ! unsigned short eodata = buf[5] | buf[6]<<8; ! unsigned short timeout = buf[7] | buf[8]<<8; ! unsigned short eoprompt = buf[9] | buf[10]<<8; ! unsigned short sodisplay = buf[11]| buf[12]<<8; ! unsigned short lowwater = buf[13]| buf[14]<<8; ! unsigned char term_len = buf[16]; ! ! // TODO flags ! ! tty_set_terminators(buf+17, term_len); ! tty_start_read(buf+17+term_len, len-term_len-16, eoprompt); ! tty_set_timeout(timeout); ! tty_set_maxlen(maxlength); ! return len; ! } ! static int cterm_process_read_data(char *buf, int len) {return len;} ! static int cterm_process_oob(char *buf, int len) {return len;} ! static int cterm_process_unread(char *buf, int len) {return len;} ! static int cterm_process_clear_input(char *buf, int len) {return len;} ! static int cterm_process_write(char *buf, int len) ! { ! unsigned short flags = buf[1] | buf[2]<<8; ! unsigned char prefixdata = buf[3]; ! unsigned char postfixdata = buf[4]; ! ! // TODO: flags... ! tty_write(buf+5, len-5); ! return len; ! } ! ! static int cterm_process_write_complete(char *buf, int len) {return len;} ! static int cterm_process_discard_state(char *buf, int len) {return len;} ! static int cterm_process_read_characteristics(char *buf, int len) {return len;} ! static int cterm_process_characteristics(char *buf, int len) {return len;} ! static int cterm_process_check_input(char *buf, int len) {return len;} ! static int cterm_process_input_count(char *buf, int len) {return len;} ! static int cterm_process_input_state(char *buf, int len) {return len;} *************** *** 99,115 **** int offset = 0; - if (debug > 3) - { - int i; - - fprintf(stderr, "got message %d bytes:\n", len); - for (i=0; i<len; i++) - fprintf(stderr, "%02x ", buf[i]); - fprintf(stderr, "\n\n"); - } - while (offset < len) { ! if (debug > 2) fprintf(stderr, "dnlogin: got msg: %d, len=%d\n", buf[offset], len); --- 135,141 ---- int offset = 0; while (offset < len) { ! if (debug > 2) fprintf(stderr, "CTERM: got msg: %d, len=%d\n", buf[offset], len); *************** *** 117,160 **** { case CTERM_MSG_INITIATE: ! offset += ct_process_initiate(buf+offset, len-offset); break; case CTERM_MSG_START_READ: ! offset += ct_process_start_read(buf+offset, len-offset); break; case CTERM_MSG_READ_DATA: ! offset += ct_process_read_data(buf+offset, len-offset); break; case CTERM_MSG_OOB: ! offset += ct_process_oob(buf+offset, len-offset); break; case CTERM_MSG_UNREAD: ! offset += ct_process_unread(buf+offset, len-offset); break; case CTERM_MSG_CLEAR_INPUT: ! offset += ct_process_clear_input(buf+offset, len-offset); break; case CTERM_MSG_WRITE: ! offset += ct_process_write(buf+offset, len-offset); break; case CTERM_MSG_WRITE_COMPLETE: ! offset += ct_process_write_complete(buf+offset, len-offset); break; case CTERM_MSG_DISCARD_STATE: ! offset += ct_process_discard_state(buf+offset, len-offset); break; case CTERM_MSG_READ_CHARACTERISTICS: ! offset += ct_process_read_characteristics(buf+offset, len-offset); break; case CTERM_MSG_CHARACTERISTINCS: ! offset += ct_process_characteristics(buf+offset, len-offset); break; case CTERM_MSG_CHECK_INPUT: ! offset += ct_process_check_input(buf+offset, len-offset); break; case CTERM_MSG_INPUT_COUNT: ! offset += ct_process_input_count(buf+offset, len-offset); break; case CTERM_MSG_INPUT_STATE: ! offset += ct_process_input_state(buf+offset, len-offset); break; --- 143,186 ---- { case CTERM_MSG_INITIATE: ! offset += cterm_process_initiate(buf+offset, len-offset); break; case CTERM_MSG_START_READ: ! offset += cterm_process_start_read(buf+offset, len-offset); break; case CTERM_MSG_READ_DATA: ! offset += cterm_process_read_data(buf+offset, len-offset); break; case CTERM_MSG_OOB: ! offset += cterm_process_oob(buf+offset, len-offset); break; case CTERM_MSG_UNREAD: ! offset += cterm_process_unread(buf+offset, len-offset); break; case CTERM_MSG_CLEAR_INPUT: ! offset += cterm_process_clear_input(buf+offset, len-offset); break; case CTERM_MSG_WRITE: ! offset += cterm_process_write(buf+offset, len-offset); break; case CTERM_MSG_WRITE_COMPLETE: ! offset += cterm_process_write_complete(buf+offset, len-offset); break; case CTERM_MSG_DISCARD_STATE: ! offset += cterm_process_discard_state(buf+offset, len-offset); break; case CTERM_MSG_READ_CHARACTERISTICS: ! offset += cterm_process_read_characteristics(buf+offset, len-offset); break; case CTERM_MSG_CHARACTERISTINCS: ! offset += cterm_process_characteristics(buf+offset, len-offset); break; case CTERM_MSG_CHECK_INPUT: ! offset += cterm_process_check_input(buf+offset, len-offset); break; case CTERM_MSG_INPUT_COUNT: ! offset += cterm_process_input_count(buf+offset, len-offset); break; case CTERM_MSG_INPUT_STATE: ! offset += cterm_process_input_state(buf+offset, len-offset); break; *************** *** 166,168 **** --- 192,208 ---- } return 0; + } + + + int cterm_write(char *buf, int len) + { + char newbuf[len+9]; + + newbuf[0] =0; + newbuf[1] =0; + newbuf[2] =0; + newbuf[3] =0; + memcpy(newbuf+4, buf, len); + + return found_common_write(newbuf, len+4); } Index: dnlogin.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnlogin/dnlogin.c,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** dnlogin.c 16 Jun 2002 18:45:24 -0000 1.1 --- dnlogin.c 18 Jun 2002 19:36:54 -0000 1.2 *************** *** 37,40 **** --- 37,41 ---- static int exit_char = 035; /* Default to ^] */ static int finished = 0; /* terminate mainloop */ + int debug = 0; *************** *** 48,52 **** --- 49,89 ---- static char esc_buf[132]; static int esc_len; + static int max_read_len = sizeof(input_buf); + static int echo = 1; + + /* Raw write to terminal */ + int tty_write(char *buf, int len) + { + return (write(termfd, buf, len) == len); + } + + void tty_set_terminators(char *buf, int len) + { + memset(terminators, 0, sizeof(terminators)); + memcpy(terminators, buf, len); + } + + void tty_start_read(char *prompt, int len, int promptlen) + { + write(termfd, prompt, len); + /* Save the actual prompt in one buffer and the prefilled + data in th input buffer */ + memcpy(prompt_buf, prompt, promptlen); + prompt_len = promptlen; + + memcpy(input_buf, prompt+promptlen, len-promptlen); + input_len = len-promptlen; + } + + void tty_set_timeout(unsigned short to) + { + // TODO: + } + + void tty_set_maxlen(unsigned short len) + { + max_read_len = len; + } /* Set/Reset the local TTY mode */ *************** *** 80,131 **** return 0; } - static const char *hosttype[] = { - "RT-11", - "RSTS/E", - "RSX-11S", - "RSX-11M", - "RSX-11D", - "IAS", - "VAX/VMS", - "TOPS-20", - "TOPS-10", - "OS8", - "RTS-8", - "RSX-11M+", - "??13", "??14", "??15", "??16", "??17", - "Ultrix-32", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "", "", - "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", - "Unix-dni" - }; /* Input from keyboard */ static int process_terminal(char *buf, int len) { ! if (buf[0] == exit_char) { ! finished = 1; ! return 0; ! } ! /* TODO: */ ! return -1; } --- 117,168 ---- return 0; } + static short is_terminator(char c) + { + short termind, msk, aux; + + termind = c / 8; + aux = c - (termind * 8); + msk = (1 << aux); + + if (terminators[termind] && msk) + { + return 1; + } + return 0; + } /* Input from keyboard */ static int process_terminal(char *buf, int len) { ! int i; ! ! for (i=0; i<len; i++) { ! if (buf[i] == exit_char) ! { ! finished = 1; ! return 0; ! } ! if (echo) ! write(termfd, &buf[i], 1); ! if (is_terminator(buf[i])) ! { ! cterm_write(&buf[i], 1); ! return 0; ! } ! ! // TODO: process line-editting keys & flags ! input_buf[input_len++] = buf[i]; ! if (input_len == max_read_len) ! { ! cterm_write(input_buf, input_len); ! } ! ! // TODO: Loads more. ! } ! return 0; } *************** *** 239,243 **** } ! if (found_setup_link(argv[optind],DNOBJECT_CTERM) == 0) { setup_tty("/dev/tty", 1); --- 276,280 ---- } ! if (found_setup_link(argv[optind], DNOBJECT_CTERM, process_cterm) == 0) { setup_tty("/dev/tty", 1); Index: dnlogin.h =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnlogin/dnlogin.h,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** dnlogin.h 16 Jun 2002 18:45:24 -0000 1.1 --- dnlogin.h 18 Jun 2002 19:36:54 -0000 1.2 *************** *** 19,25 **** extern int found_write(char *buf, int len); extern int found_read(void); ! extern int found_setup_link(char *node, int object); extern int process_cterm(char *buf, int len); extern int debug; --- 19,29 ---- extern int found_write(char *buf, int len); extern int found_read(void); ! extern int found_setup_link(char *node, int object, int (*processor)(char *, int)); ! extern int found_common_write(char *buf, int len); ! ! extern int process_cterm(char *buf, int len); + extern int tty_write(char *buf, int len); extern int debug; Index: found.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnlogin/found.c,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** found.c 16 Jun 2002 18:45:24 -0000 1.1 --- found.c 18 Jun 2002 19:36:54 -0000 1.2 *************** *** 29,52 **** #include <netdnet/dn.h> #include <netdnet/dnetdb.h> - #include "cterm.h" #include "dn_endian.h" #include "dnlogin.h" static int sockfd = -1; ! static int send_bind(void) { int wrote; ! unsigned char bindmsg[] = { ! // TODO annotate correctly ! 4, ! 2,4,0, ! 7,0, ! 16,0, }; ! wrote = write(sockfd, bindmsg, sizeof(bindmsg)); ! if (wrote != sizeof(bindmsg)) { fprintf(stderr, "%s\n", found_connerror("read error")); --- 29,110 ---- #include <netdnet/dn.h> #include <netdnet/dnetdb.h> #include "dn_endian.h" #include "dnlogin.h" + + /* Foundation services messages */ + #define FOUND_MSG_BIND 1 + #define FOUND_MSG_UNBIND 3 + #define FOUND_MSG_BINDACCEPT 4 + #define FOUND_MSG_ENTERMODE 5 + #define FOUND_MSG_EXITMODE 6 + #define FOUND_MSG_CONFIRMMODE 7 + #define FOUND_MSG_NOMODE 8 + #define FOUND_MSG_COMMONDATA 9 + #define FOUND_MSG_MODEDATA 10 + + + static const char *hosttype[] = { + "RT-11", + "RSTS/E", + "RSX-11S", + "RSX-11M", + "RSX-11D", + "IAS", + "VMS", + "TOPS-20", + "TOPS-10", + "OS8", + "RTS-8", + "RSX-11M+", + "??13", "??14", "??15", "??16", "??17", + "Ultrix-32", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "", "", + "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", + "Unix-dni" + }; + + + /* Header for a single-message "common data" message */ + struct common_header + { + unsigned char msg; + unsigned char pad; + unsigned short len; + }; + + static int sockfd = -1; + static int (*terminal_processor)(char *, int); ! static int send_bindaccept(void) { int wrote; ! unsigned char bindacc_msg[] = { ! FOUND_MSG_BINDACCEPT, ! 2,4,0, /* Version triplet */ ! 7,0, /* OS = VMS */ ! 0x10, /* We talk terminal protocol */ ! 0, /* Empty rev string */ }; ! wrote = write(sockfd, bindacc_msg, sizeof(bindacc_msg)); ! if (wrote != sizeof(bindacc_msg)) { fprintf(stderr, "%s\n", found_connerror("read error")); *************** *** 62,69 **** } ! int found_write(char *buf, int len) { ! // TODO: write header then message with EOR using sendmsg ! return -1; } --- 120,150 ---- } ! /* Write "Common data" with a foundation header */ ! int found_common_write(char *buf, int len) { ! struct iovec vectors[2]; ! struct msghdr msg; ! struct common_header header; ! ! memset(&msg, 0, sizeof(msg)); ! vectors[0].iov_base = (void *)&header; ! vectors[0].iov_len = sizeof(header); ! vectors[1].iov_base = buf; ! vectors[1].iov_len = len; ! ! msg.msg_name = NULL; ! msg.msg_namelen = 0; ! msg.msg_iovlen = 2; ! msg.msg_iov = vectors; ! msg.msg_flags = 0; ! ! header.msg = FOUND_MSG_COMMONDATA; ! header.pad = 0; ! header.len = dn_htons(len); ! ! if (debug > 2) ! fprintf(stderr, "FOUND: sending common message %d bytes:\n", len); ! ! return sendmsg(sockfd, &msg, MSG_EOR); } *************** *** 73,92 **** char inbuf[1024]; ! if ( (len=dnet_recv(sockfd, inbuf, sizeof(inbuf), MSG_EOR|MSG_DONTWAIT)) ! <= 0) { fprintf(stderr, "%s\n", found_connerror("read sock")); return -1; } ! /* TODO: something about the foundation message codes */ ! /* TODO: Know the protocol, switch cterm/dterm etc? */ ! return process_cterm(inbuf+4, len-4); } /* Open the DECnet connection */ ! int found_setup_link(char *node, int object) { struct nodeent *np; --- 154,200 ---- char inbuf[1024]; ! if ( (len=dnet_recv(sockfd, inbuf, sizeof(inbuf), MSG_EOR|MSG_DONTWAIT)) <= 0) { + if (len == -1 && errno == EAGAIN) + return 0; + fprintf(stderr, "%s\n", found_connerror("read sock")); return -1; } ! if (debug > 2) ! fprintf(stderr, "FOUND: got message %d bytes:\n", len); ! if (debug > 3) ! { ! int i; ! ! for (i=0; i<len; i++) ! fprintf(stderr, "%02x ", (unsigned char)inbuf[i]); ! fprintf(stderr, "\n\n"); ! } ! ! /* Dispatch a foundation message */ ! switch (inbuf[0]) ! { ! case FOUND_MSG_BIND: ! if (debug) ! printf("connected to %s host\n", hosttype[inbuf[4]-1]); ! return send_bindaccept(); ! ! /* Common data goes straight to the terminal processor */ ! case FOUND_MSG_COMMONDATA: ! return terminal_processor(inbuf+4, len-4); ! ! default: ! fprintf(stderr, "Unknown foundation services message %d received\n", ! inbuf[0]); ! } ! return -1; } /* Open the DECnet connection */ ! int found_setup_link(char *node, int object, int (*processor)(char *, int)) { struct nodeent *np; *************** *** 121,125 **** } ! return send_bind(); } --- 229,234 ---- } ! terminal_processor = processor; ! return 0; } |
From: Patrick C. <pa...@us...> - 2002-06-16 18:58:10
|
Update of /cvsroot/linux-decnet/dnprogs/dnlogin In directory usw-pr-cvs1:/tmp/cvs-serv15831 Added Files: Makefile Log Message: Makefile for dnlogin --- NEW FILE: Makefile --- # Makefile for dnlogin include ../Makefile.common CFLAGS+=-I../apps PROG1=dnlogin MANPAGES=dnlogin.1 PROG1OBJS=dnlogin.o found.o cterm.o all: $(PROG1) $(PROG1): $(PROG1OBJS) $(DEPLIBDNET) $(CC) -o $@ $(PROG1OBJS) $(LIBDNET) install: install -d $(prefix)/bin install -d $(prefix)/man/man1 install -m 0755 -s $(PROG1) $(prefix)/bin install -m 0644 $(MANPAGES) $(prefix)/man/man1 dep depend: $(CC) $(CFLAGS) -MM *.c >.depend 2>/dev/null clean: rm -f $(PROG1) *.o *.bak .depend ifeq (.depend,$(wildcard .depend)) include .depend endif |
From: Patrick C. <pa...@us...> - 2002-06-16 18:45:27
|
Update of /cvsroot/linux-decnet/dnprogs/dnlogin In directory usw-pr-cvs1:/tmp/cvs-serv12966 Added Files: cterm.c dnlogin.c dnlogin.h found.c Log Message: New files for the new dnlogin program. Don't get too excited this is just a rewrite of sethost.c. The files here are more of a framework than a program. It doesn't work and won't for some time yet, but I would appreciate any help :-) --- NEW FILE: cterm.c --- /****************************************************************************** (c) 2002 P.J. Caulfield pa...@de... This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. ****************************************************************************** */ #include <stdio.h> #include <string.h> #include <errno.h> #include <unistd.h> #include <signal.h> #include <stdlib.h> #include <ctype.h> #include <termios.h> #include <sys/socket.h> #include <sys/ioctl.h> #include <sys/types.h> #include <sys/time.h> #include <sys/fcntl.h> #include <netdnet/dn.h> #include <netdnet/dnetdb.h> #include "cterm.h" #include "dn_endian.h" #include "dnlogin.h" #define CTERM_MSG_INITIATE 1 #define CTERM_MSG_START_READ 2 #define CTERM_MSG_READ_DATA 3 #define CTERM_MSG_OOB 4 #define CTERM_MSG_UNREAD 5 #define CTERM_MSG_CLEAR_INPUT 6 #define CTERM_MSG_WRITE 7 #define CTERM_MSG_WRITE_COMPLETE 8 #define CTERM_MSG_DISCARD_STATE 9 #define CTERM_MSG_READ_CHARACTERISTICS 10 #define CTERM_MSG_CHARACTERISTINCS 11 #define CTERM_MSG_CHECK_INPUT 12 #define CTERM_MSG_INPUT_COUNT 13 #define CTERM_MSG_INPUT_STATE 14 /* Process incoming CTERM messages */ static int ct_process_initiate(char *buf, int len) { return len; } static int ct_process_start_read(char *buf, int len) {return len;} static int ct_process_read_data(char *buf, int len) {return len;} static int ct_process_oob(char *buf, int len) {return len;} static int ct_process_unread(char *buf, int len) {return len;} static int ct_process_clear_input(char *buf, int len) {return len;} static int ct_process_write(char *buf, int len) {return len;} static int ct_process_write_complete(char *buf, int len) {return len;} static int ct_process_discard_state(char *buf, int len) {return len;} static int ct_process_read_characteristics(char *buf, int len) {return len;} static int ct_process_characteristics(char *buf, int len) {return len;} static int ct_process_check_input(char *buf, int len) {return len;} static int ct_process_input_count(char *buf, int len) {return len;} static int ct_process_input_state(char *buf, int len) {return len;} /* Process buffer from cterm host */ int process_cterm(char *buf, int len) { int offset = 0; if (debug > 3) { int i; fprintf(stderr, "got message %d bytes:\n", len); for (i=0; i<len; i++) fprintf(stderr, "%02x ", buf[i]); fprintf(stderr, "\n\n"); } while (offset < len) { if (debug > 2) fprintf(stderr, "dnlogin: got msg: %d, len=%d\n", buf[offset], len); switch (buf[offset]) { case CTERM_MSG_INITIATE: offset += ct_process_initiate(buf+offset, len-offset); break; case CTERM_MSG_START_READ: offset += ct_process_start_read(buf+offset, len-offset); break; case CTERM_MSG_READ_DATA: offset += ct_process_read_data(buf+offset, len-offset); break; case CTERM_MSG_OOB: offset += ct_process_oob(buf+offset, len-offset); break; case CTERM_MSG_UNREAD: offset += ct_process_unread(buf+offset, len-offset); break; case CTERM_MSG_CLEAR_INPUT: offset += ct_process_clear_input(buf+offset, len-offset); break; case CTERM_MSG_WRITE: offset += ct_process_write(buf+offset, len-offset); break; case CTERM_MSG_WRITE_COMPLETE: offset += ct_process_write_complete(buf+offset, len-offset); break; case CTERM_MSG_DISCARD_STATE: offset += ct_process_discard_state(buf+offset, len-offset); break; case CTERM_MSG_READ_CHARACTERISTICS: offset += ct_process_read_characteristics(buf+offset, len-offset); break; case CTERM_MSG_CHARACTERISTINCS: offset += ct_process_characteristics(buf+offset, len-offset); break; case CTERM_MSG_CHECK_INPUT: offset += ct_process_check_input(buf+offset, len-offset); break; case CTERM_MSG_INPUT_COUNT: offset += ct_process_input_count(buf+offset, len-offset); break; case CTERM_MSG_INPUT_STATE: offset += ct_process_input_state(buf+offset, len-offset); break; default: fprintf(stderr, "Unknown cterm message %d received\n", buf[offset]); return -1; } } return 0; } --- NEW FILE: dnlogin.c --- /****************************************************************************** (c) 2002 P.J. Caulfield pa...@de... This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. ****************************************************************************** */ #include <stdio.h> #include <string.h> #include <errno.h> #include <unistd.h> #include <signal.h> #include <stdlib.h> #include <ctype.h> #include <termios.h> #include <sys/socket.h> #include <sys/ioctl.h> #include <sys/types.h> #include <sys/time.h> #include <sys/fcntl.h> #include <netdnet/dn.h> #include <netdnet/dnetdb.h> #include "cterm.h" #include "dn_endian.h" #include "dnlogin.h" /* The global state */ static int termfd = -1; static int exit_char = 035; /* Default to ^] */ static int finished = 0; /* terminate mainloop */ int debug = 0; /* Input state buffers & variables */ static unsigned char terminators[32]; static char input_buf[1024]; static int input_len; static char prompt_buf[1024]; static char prompt_len; static char esc_buf[132]; static int esc_len; /* Set/Reset the local TTY mode */ static int setup_tty(char *name, int setup) { struct termios new_term; static struct termios old_term; if (setup) { termfd = open(name, O_RDWR); tcgetattr(termfd, &old_term); new_term = old_term; new_term.c_iflag &= ~BRKINT; new_term.c_iflag |= IGNBRK; new_term.c_lflag &= ~ISIG; new_term.c_cc[VMIN] = 1; new_term.c_cc[VTIME] = 0; new_term.c_lflag &= ~ICANON; new_term.c_lflag &= ~(ECHO | ECHOCTL | ECHONL); tcsetattr(termfd, TCSANOW, &new_term); } else { tcsetattr(termfd, TCSANOW, &old_term); close(termfd); } return 0; } static const char *hosttype[] = { "RT-11", "RSTS/E", "RSX-11S", "RSX-11M", "RSX-11D", "IAS", "VAX/VMS", "TOPS-20", "TOPS-10", "OS8", "RTS-8", "RSX-11M+", "??13", "??14", "??15", "??16", "??17", "Ultrix-32", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "Unix-dni" }; /* Input from keyboard */ static int process_terminal(char *buf, int len) { if (buf[0] == exit_char) { finished = 1; return 0; } /* TODO: */ return -1; } static int mainloop(void) { while (!finished) { char inbuf[1024]; fd_set in_set; FD_ZERO(&in_set); FD_SET(termfd, &in_set); FD_SET(found_getsockfd(), &in_set); if (select(FD_SETSIZE, &in_set, NULL, NULL, NULL) < 0) { break; } /* Read from keyboard */ if (FD_ISSET(termfd, &in_set)) { int len; if ( (len=read(termfd, inbuf, sizeof(inbuf))) <= 0) { perror("read tty"); break; } process_terminal(inbuf, len); } if (found_read() == -1) break; } return 0; } static void set_exit_char(char *string) { int newchar = 0; if (string[0] == '^') { newchar = toupper(string[1]) - '@'; } else newchar = strtol(string, NULL, 0); // Just a number // Make sure it's resaonable if (newchar > 0 && newchar < 256) exit_char = newchar; } static void usage(char *prog, FILE * f) { fprintf(f, "\nUSAGE: %s [OPTIONS] node\n\n", prog); fprintf(f, "\nOptions:\n"); fprintf(f, " -? -h display this help message\n"); fprintf(f, " -V show version number\n"); fprintf(f, " -e <char> set escape char\n"); fprintf(f, " -d debug information\n"); fprintf(f, "\n"); } int main(int argc, char *argv[]) { struct sigaction sa; sigset_t ss; int opt; char *nodename; // Deal with command-line arguments. opterr = 0; optind = 0; while ((opt = getopt(argc, argv, "?Vhdte:")) != EOF) { switch (opt) { case 'h': usage(argv[0], stdout); exit(0); case '?': usage(argv[0], stderr); exit(0); case 'V': printf("\ndnlogin from dnprogs version %s\n\n", VERSION); exit(1); break; case 'e': set_exit_char(optarg); break; case 'd': debug++; break; } } if (optind >= argc) { usage(argv[0], stderr); exit(2); } if (found_setup_link(argv[optind],DNOBJECT_CTERM) == 0) { setup_tty("/dev/tty", 1); mainloop(); setup_tty(NULL, 0); } else { return 2; } return 0; } --- NEW FILE: dnlogin.h --- /****************************************************************************** (c) 2002 P.J. Caulfield pa...@de... This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. ****************************************************************************** */ extern char *found_connerror(char *default_msg); extern int found_getsockfd(void); extern int found_write(char *buf, int len); extern int found_read(void); extern int found_setup_link(char *node, int object); extern int process_cterm(char *buf, int len); extern int debug; --- NEW FILE: found.c --- /****************************************************************************** (c) 2002 P.J. Caulfield pa...@de... This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. ****************************************************************************** */ #include <stdio.h> #include <string.h> #include <errno.h> #include <unistd.h> #include <signal.h> #include <stdlib.h> #include <ctype.h> #include <termios.h> #include <sys/socket.h> #include <sys/ioctl.h> #include <sys/types.h> #include <sys/time.h> #include <sys/fcntl.h> #include <netdnet/dn.h> #include <netdnet/dnetdb.h> #include "cterm.h" #include "dn_endian.h" #include "dnlogin.h" static int sockfd = -1; static int send_bind(void) { int wrote; unsigned char bindmsg[] = { // TODO annotate correctly 4, 2,4,0, 7,0, 16,0, }; wrote = write(sockfd, bindmsg, sizeof(bindmsg)); if (wrote != sizeof(bindmsg)) { fprintf(stderr, "%s\n", found_connerror("read error")); return -1; } return 0; } int found_getsockfd() { return sockfd; } int found_write(char *buf, int len) { // TODO: write header then message with EOR using sendmsg return -1; } int found_read() { int len; char inbuf[1024]; if ( (len=dnet_recv(sockfd, inbuf, sizeof(inbuf), MSG_EOR|MSG_DONTWAIT)) <= 0) { fprintf(stderr, "%s\n", found_connerror("read sock")); return -1; } /* TODO: something about the foundation message codes */ /* TODO: Know the protocol, switch cterm/dterm etc? */ return process_cterm(inbuf+4, len-4); } /* Open the DECnet connection */ int found_setup_link(char *node, int object) { struct nodeent *np; struct sockaddr_dn sockaddr; if ( (np=getnodebyname(node)) == NULL) { printf("Unknown node name %s\n",node); return -1; } if ((sockfd = socket(AF_DECnet, SOCK_SEQPACKET, DNPROTO_NSP)) == -1) { perror("socket"); return -1; } sockaddr.sdn_family = AF_DECnet; sockaddr.sdn_flags = 0x00; sockaddr.sdn_objnum = object; sockaddr.sdn_objnamel = 0x00; sockaddr.sdn_add.a_len = 0x02; memcpy(sockaddr.sdn_add.a_addr, np->n_addr, 2); if (connect(sockfd, (struct sockaddr *) &sockaddr, sizeof(sockaddr)) < 0) { perror("socket"); return -1; } return send_bind(); } /* Return the text of a connection error */ char *found_connerror(char *default_msg) { #ifdef DSO_DISDATA struct optdata_dn optdata; unsigned int len = sizeof(optdata); char *msg; if (getsockopt(sockfd, DNPROTO_NSP, DSO_DISDATA, &optdata, &len) == -1) { return default_msg; } // Turn the rejection reason into text switch (optdata.opt_status) { case DNSTAT_REJECTED: msg="Rejected by object"; break; case DNSTAT_RESOURCES: msg="No resources available"; break; case DNSTAT_NODENAME: msg="Unrecognised node name"; break; case DNSTAT_LOCNODESHUT: msg="Local Node is shut down"; break; case DNSTAT_OBJECT: msg="Unrecognised object"; break; case DNSTAT_OBJNAMEFORMAT: msg="Invalid object name format"; break; case DNSTAT_TOOBUSY: msg="Object too busy"; break; case DNSTAT_NODENAMEFORMAT: msg="Invalid node name format"; break; case DNSTAT_REMNODESHUT: msg="Remote Node is shut down"; break; case DNSTAT_ACCCONTROL: msg="Login information invalid at remote node"; break; case DNSTAT_NORESPONSE: msg="No response from object"; break; case DNSTAT_NODEUNREACH: msg="Node Unreachable"; break; case DNSTAT_MANAGEMENT: msg="Abort by management/third party"; break; case DNSTAT_ABORTOBJECT: msg="Remote object aborted the link"; break; case DNSTAT_NODERESOURCES: msg="Node does not have sufficient resources for a new link"; break; case DNSTAT_OBJRESOURCES: msg="Object does not have sufficient resources for a new link"; break; case DNSTAT_BADACCOUNT: msg="The Account field in unacceptable"; break; case DNSTAT_TOOLONG: msg="A field in the access control message was too long"; break; default: msg=default_msg; break; } return msg; #else return strerror(errno); #endif } |
From: Patrick C. <pa...@us...> - 2002-06-16 18:35:29
|
Update of /cvsroot/linux-decnet/dnprogs/dnlogin In directory usw-pr-cvs1:/tmp/cvs-serv11087/dnlogin Log Message: Directory /cvsroot/linux-decnet/dnprogs/dnlogin added to the repository |
From: Patrick C. <pa...@us...> - 2002-06-07 13:16:51
|
Update of /cvsroot/linux-decnet/latd In directory usw-pr-cvs1:/tmp/cvs-serv27880 Modified Files: latcp.cc Log Message: back out last change (using realpath()) cos it doesn't work. Index: latcp.cc =================================================================== RCS file: /cvsroot/linux-decnet/latd/latcp.cc,v retrieving revision 1.34 retrieving revision 1.35 diff -C2 -r1.34 -r1.35 *** latcp.cc 3 Apr 2002 13:40:32 -0000 1.34 --- latcp.cc 7 Jun 2002 13:16:48 -0000 1.35 *************** *** 772,776 **** } } - // Otherwise look in some well-known places else if (!stat("/usr/sbin/latd", &st)) --- 772,775 ---- *************** *** 791,799 **** char *newenv[4]; int i; char latcp_bin[PATH_MAX]; char latcp_env[PATH_MAX+7]; ! realpath(argv[0], latcp_bin); sprintf(latcp_env, "LATCP=%s", latcp_bin); --- 790,811 ---- char *newenv[4]; int i; + char latcp_proc[PATH_MAX]; char latcp_bin[PATH_MAX]; char latcp_env[PATH_MAX+7]; ! // This is VERY Linux specific and needs /proc mounted. ! // we get the full path of the current executable by doing a readlink. ! // /proc/<pid>/exe + #ifdef __linux__ + sprintf(latcp_proc, "/proc/%d/exe", getpid()); + if ( (i=readlink(latcp_proc, latcp_bin, sizeof(latcp_bin))) == -1) + { + fprintf(stderr, "readlink in /proc failed. Make sure the the proc filesystem is mounted on /proc\n"); + exit(2); + } + #else + #error OK, a bit more porting work needed here too. + #endif sprintf(latcp_env, "LATCP=%s", latcp_bin); |
From: Patrick C. <pa...@us...> - 2002-05-19 12:53:16
|
Update of /cvsroot/linux-decnet/latd In directory usw-pr-cvs1:/tmp/cvs-serv7779 Modified Files: INSTALL README Log Message: Minor doc updates. Index: INSTALL =================================================================== RCS file: /cvsroot/linux-decnet/latd/INSTALL,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -r1.4 -r1.5 *** INSTALL 12 Feb 2002 13:36:17 -0000 1.4 --- INSTALL 19 May 2002 12:53:13 -0000 1.5 *************** *** 1,8 **** Just type "make; make install" There are a few things you can tweak in the Makefile: See the lines: ! DEFS+=-DUSE_OPENPTY #-DSETLOGIN_HOST #DEFS+=-DVERBOSE_DEBUG -DNO_FORK --- 1,12 ---- Just type "make; make install" + You will need to arrange for the daemon to be started when the system boots + up, add the command "latcp -s" to a suitable startup script. + + There are a few things you can tweak in the Makefile: See the lines: ! DEFS+=-DUSE_OPENPTY #DEFS+=-DVERBOSE_DEBUG -DNO_FORK *************** *** 15,26 **** to generate the pairs of pseudo-terminals. Without this it will use old-style code. If you have a RedHat 5.2 (or similar vintage) distribution you might ! need to remove this to get latd to work. Any system with glibc 2.1.3 will be ! fine with it though. ! ! -DSETLOGIN_HOST ! This depends on your login command. It works fine on RedHat 6.0+ and Debian ! 2.1+ but not on SuSE 6.4 or Redhat 5.x so I've left it commented out by ! default. If you define it then the "who" command will show the name of the ! terminal server/host you came from. -DNO_FORK prevent the daemon from forking into the background when run. Without --- 19,24 ---- to generate the pairs of pseudo-terminals. Without this it will use old-style code. If you have a RedHat 5.2 (or similar vintage) distribution you might ! need to remove this to get latd to work. Any system with glibc 2.1.3 or ! later will be fine with it though. -DNO_FORK prevent the daemon from forking into the background when run. Without Index: README =================================================================== RCS file: /cvsroot/linux-decnet/latd/README,v retrieving revision 1.8 retrieving revision 1.9 diff -C2 -r1.8 -r1.9 *** README 20 Mar 2002 16:54:47 -0000 1.8 --- README 19 May 2002 12:53:13 -0000 1.9 *************** *** 42,46 **** LATD itself currently only runs on Linux but it shouldn't be too hard to port to other Unix-like platforms by writing an interface class for ! that platform. The following systems I know to work with LATD because I have tested them, --- 42,46 ---- LATD itself currently only runs on Linux but it shouldn't be too hard to port to other Unix-like platforms by writing an interface class for ! that platform, I have tried hard to keep the rest of the code portable. The following systems I know to work with LATD because I have tested them, *************** *** 61,65 **** I am also very much indebted to Real Dupeux for sending me a DECserver 200 for ! the project, without which is would be much impoverished. I use it a for reverse-LAT every day of the week to log in to the consoles of my VAX, Alpha, SPARC and MIPS machines. --- 61,65 ---- I am also very much indebted to Real Dupeux for sending me a DECserver 200 for ! the project, without which it would be much impoverished. I use it a for reverse-LAT every day of the week to log in to the consoles of my VAX, Alpha, SPARC and MIPS machines. |
From: Patrick C. <pa...@us...> - 2002-05-19 12:34:03
|
Update of /cvsroot/linux-decnet/latd In directory usw-pr-cvs1:/tmp/cvs-serv4230 Modified Files: serversession.cc serversession.h Log Message: Close all FDs before forking child process. Index: serversession.cc =================================================================== RCS file: /cvsroot/linux-decnet/latd/serversession.cc,v retrieving revision 1.13 retrieving revision 1.14 diff -C2 -r1.13 -r1.14 *** serversession.cc 11 Feb 2002 16:39:34 -0000 1.13 --- serversession.cc 19 May 2002 12:33:59 -0000 1.14 *************** *** 14,17 **** --- 14,18 ---- #include <sys/types.h> + #include <sys/resource.h> #include <stdio.h> #include <syslog.h> *************** *** 178,181 **** --- 179,184 ---- if (fd > 2) close (fd); + close_all_fds(); + setsid(); *************** *** 214,217 **** --- 217,245 ---- return 0; } + + /* Hopefully this will work for BSDs + as well as Linux */ + #ifdef RLIMIT_NOFILE + # define LAT_RLIMIT_FILES RLIMIT_NOFILE + #else + # ifdef RLIMIT_OFILE + # define LAT_RLIMIT_FILES RLIMIT_OFILE + # endif + #endif + + void ServerSession::close_all_fds() + { + struct rlimit rl; + + if (getrlimit(LAT_RLIMIT_FILES, &rl) == -1) + rl.rlim_cur = 256; + if (rl.rlim_cur == RLIM_INFINITY) + rl.rlim_cur = 256; + + for (unsigned int i=3; i<rl.rlim_cur; i++) + close(i); + } + + void ServerSession::execute_command(const char *command) Index: serversession.h =================================================================== RCS file: /cvsroot/linux-decnet/latd/serversession.h,v retrieving revision 1.5 retrieving revision 1.6 diff -C2 -r1.5 -r1.6 *** serversession.h 3 Jan 2002 08:46:55 -0000 1.5 --- serversession.h 19 May 2002 12:33:59 -0000 1.6 *************** *** 36,38 **** --- 36,39 ---- int create_session(unsigned char *remote_node); void execute_command(const char *command); + void close_all_fds(); }; |
From: Patrick C. <pa...@us...> - 2002-04-18 09:08:00
|
Update of /cvsroot/linux-decnet/dnprogs/dnroute In directory usw-pr-cvs1:/tmp/cvs-serv10030 Modified Files: README Log Message: Some notes on use. to remind me as much as anything else. Index: README =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnroute/README,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** README 19 Dec 2000 16:02:51 -0000 1.1 --- README 18 Apr 2002 09:07:56 -0000 1.2 *************** *** 13,14 **** --- 13,19 ---- If you want to test DECnet routing please contact myself (patrick) or Steve Whitehouse via the linux-decnet-user mailing list. + + NOTES: + insert the :grabulator: module dn_rtmsg.o + echo "1" into /proc/sys/net/decnet/conf/eth<x>/forwarding + echo "1" into /proc/sys/net/decnet/conf/eth<x>/priority (Must NOT be 0) |
From: Patrick C. <pa...@us...> - 2002-04-17 16:06:27
|
Update of /cvsroot/linux-decnet/dnprogs/dnroute In directory usw-pr-cvs1:/tmp/cvs-serv26302 Modified Files: Makefile dn_rtmsg.c dnroute.c send_route.c Log Message: dnroute fixes for latest kernel. Steves new grabulator code. Index: Makefile =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnroute/Makefile,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** Makefile 19 Dec 2000 16:02:51 -0000 1.1 --- Makefile 17 Apr 2002 16:06:23 -0000 1.2 *************** *** 3,7 **** DNROUTE=dnroute ! CC=gcc -g -Wall -fstrict-prototypes -I$(IPROUTE2)include all: $(DNROUTE) --- 3,7 ---- DNROUTE=dnroute ! CC=gcc -g -Wall -fstrict-prototypes -I$(IPROUTE2)/include all: $(DNROUTE) Index: dn_rtmsg.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnroute/dn_rtmsg.c,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** dn_rtmsg.c 20 May 2001 12:31:59 -0000 1.1 --- dn_rtmsg.c 17 Apr 2002 16:06:23 -0000 1.2 *************** *** 20,25 **** #include <linux/spinlock.h> #include <linux/netlink.h> - #include <linux/rtnetlink.h> - #include <asm/semaphore.h> #include <net/sock.h> --- 20,23 ---- *************** *** 30,36 **** static struct sock *dnrmg = NULL; - extern struct semaphore rtnl_sem; - static struct sk_buff *netlink_build_message(struct sk_buff *rt_skb, int *errp) { --- 28,37 ---- static struct sock *dnrmg = NULL; + /* + * The message sent by this function consists of the interface index of + * the interface on which the routing message was received followed by + * the message itself. + */ static struct sk_buff *netlink_build_message(struct sk_buff *rt_skb, int *errp) { *************** *** 50,54 **** nlh = NLMSG_PUT(skb, 0, 0, 0, size - sizeof(*nlh)); rtm = (struct nf_dn_rtmsg *)NLMSG_DATA(nlh); ! rtm->nfdn_ifindex = rt_skb->rx_dev->ifindex; ptr = NFDN_RTMSG(rtm); memcpy(ptr, rt_skb->data, rt_skb->len); --- 51,55 ---- nlh = NLMSG_PUT(skb, 0, 0, 0, size - sizeof(*nlh)); rtm = (struct nf_dn_rtmsg *)NLMSG_DATA(nlh); ! rtm->nfdn_ifindex = rt_skb->dev->ifindex; ptr = NFDN_RTMSG(rtm); memcpy(ptr, rt_skb->data, rt_skb->len); *************** *** 64,68 **** } ! static int netlink_send_peer(struct sk_buff *skb) { struct sk_buff *skb2; --- 65,69 ---- } ! static void netlink_send_peer(struct sk_buff *skb) { struct sk_buff *skb2; *************** *** 79,91 **** break; default: ! return -EINVAL; } skb2 = netlink_build_message(skb, &status); if (skb2 == NULL) ! return status; NETLINK_CB(skb2).dst_groups = group; netlink_broadcast(dnrmg, skb2, 0, group, GFP_ATOMIC); - return 0; } --- 80,91 ---- break; default: ! return; } skb2 = netlink_build_message(skb, &status); if (skb2 == NULL) ! return; NETLINK_CB(skb2).dst_groups = group; netlink_broadcast(dnrmg, skb2, 0, group, GFP_ATOMIC); } *************** *** 106,114 **** static __inline__ void netlink_receive_user_skb(struct sk_buff *skb) { ! struct nlmsghdr *nlh=(struct nlmsghdr *)skb->data; ! if (!cap_raised(NETLINK_CB(skb).eff_cap, CAP_NET_ADMIN)) RCV_SKB_FAIL(-EPERM); RCV_SKB_FAIL(-EINVAL); } --- 106,122 ---- static __inline__ void netlink_receive_user_skb(struct sk_buff *skb) { ! struct nlmsghdr *nlh = (struct nlmsghdr *)skb->data; ! ! if (nlh->nlmsg_len < sizeof(*nlh) || skb->len < nlh->nlmsg_len) ! return; ! if (!cap_raised(NETLINK_CB(skb).eff_cap, CAP_NET_ADMIN)) RCV_SKB_FAIL(-EPERM); + /* + * In future this will probably be the preferred way to send + * DECnet routing messages, for now we use raw sockets though. + */ + RCV_SKB_FAIL(-EINVAL); } *************** *** 116,132 **** static void netlink_receive_user_sk(struct sock *sk, int len) { ! do { ! struct sk_buff *skb; ! if (rtnl_shlock_nowait()) ! return; ! ! while((skb = skb_dequeue(&sk->receive_queue)) != NULL) { ! netlink_receive_user_skb(skb); ! kfree_skb(skb); ! } ! ! up(&rtnl_sem); ! } while(dnrmg && skb_queue_len(&dnrmg->receive_queue)); } --- 124,133 ---- static void netlink_receive_user_sk(struct sock *sk, int len) { ! struct sk_buff *skb; ! while((skb = skb_dequeue(&sk->receive_queue)) != NULL) { ! netlink_receive_user_skb(skb); ! kfree_skb(skb); ! } } *************** *** 159,167 **** } ! MODULE_DESCRIPTION("DECnet Routing Message Grabulator"); MODULE_AUTHOR("Steven Whitehouse <st...@ch...>"); module_init(init); module_exit(fini); - --- 160,168 ---- } ! EXPORT_NO_SYMBOLS; MODULE_DESCRIPTION("DECnet Routing Message Grabulator"); MODULE_AUTHOR("Steven Whitehouse <st...@ch...>"); + MODULE_LICENSE("GPL"); module_init(init); module_exit(fini); Index: dnroute.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnroute/dnroute.c,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -r1.1 -r1.2 *** dnroute.c 19 Dec 2000 16:02:51 -0000 1.1 --- dnroute.c 17 Apr 2002 16:06:23 -0000 1.2 *************** *** 22,25 **** --- 22,26 ---- #include <sys/time.h> #include <net/if.h> + #include <net/if_arp.h> #include <netinet/in.h> #include <string.h> Index: send_route.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/dnroute/send_route.c,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -r1.2 -r1.3 *** send_route.c 6 Aug 2001 14:07:00 -0000 1.2 --- send_route.c 17 Apr 2002 16:06:23 -0000 1.3 *************** *** 28,31 **** --- 28,33 ---- #include <netpacket/packet.h> #include <net/ethernet.h> /* the L2 protocols */ + #include <net/if.h> + #include <net/if_arp.h> #else #include <asm/types.h> |
From: Patrick C. <pa...@us...> - 2002-04-17 14:45:17
|
Update of /cvsroot/linux-decnet/dnprogs/apps In directory usw-pr-cvs1:/tmp/cvs-serv28744 Modified Files: dnping.c Log Message: Typo in select command (wrong timeval struct) Index: dnping.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/apps/dnping.c,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -r1.4 -r1.5 *** dnping.c 17 Apr 2002 07:42:31 -0000 1.4 --- dnping.c 17 Apr 2002 14:45:14 -0000 1.5 *************** *** 424,428 **** timeout.tv_usec = 0; ! status = select(sockfd+1, &in_fd, NULL, NULL, &tv); if (status < 0) { --- 424,428 ---- timeout.tv_usec = 0; ! status = select(sockfd+1, &in_fd, NULL, NULL, &timeout); if (status < 0) { *************** *** 438,441 **** --- 438,442 ---- } } + num = read(sockfd,ibuf,sizeof(ibuf)); if ( num < 0 ) |
From: Patrick C. <pa...@us...> - 2002-04-17 09:47:41
|
Update of /cvsroot/linux-decnet/dnprogs/mail/uulib In directory usw-pr-cvs1:/tmp/cvs-serv17422/uulib Modified Files: Makefile Log Message: Don't die on EINTR Index: Makefile =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/mail/uulib/Makefile,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -r1.2 -r1.3 *** Makefile 31 Oct 2001 09:54:12 -0000 1.2 --- Makefile 17 Apr 2002 09:47:38 -0000 1.3 *************** *** 26,30 **** # C Compiler Options # ! CFLAGS = -fsigned-char -O -I. -DHAVE_CONFIG_H # # the ranlib program --- 26,30 ---- # C Compiler Options # ! CFLAGS = -Wall -fsigned-char -O -I. -DHAVE_CONFIG_H # # the ranlib program |
From: Patrick C. <pa...@us...> - 2002-04-17 09:47:41
|
Update of /cvsroot/linux-decnet/dnprogs/mail In directory usw-pr-cvs1:/tmp/cvs-serv17422 Modified Files: receive.c Log Message: Don't die on EINTR Index: receive.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/mail/receive.c,v retrieving revision 1.5 retrieving revision 1.6 diff -C2 -r1.5 -r1.6 *** receive.c 6 Aug 2001 14:07:00 -0000 1.5 --- receive.c 17 Apr 2002 09:47:38 -0000 1.6 *************** *** 562,565 **** --- 562,568 ---- { stat = read(dnsock, buf, sizeof(buf)); + if (stat == -1 && errno == EINTR) + continue; + if (stat == -1 && errno != ENOTCONN) { |
From: Patrick C. <pa...@us...> - 2002-04-17 09:45:10
|
Update of /cvsroot/linux-decnet/dnprogs/debian In directory usw-pr-cvs1:/tmp/cvs-serv16816 Modified Files: dnet-progs.init.d Log Message: Don't give errors when stopping on a system with no DECnet in the kernel Index: dnet-progs.init.d =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/debian/dnet-progs.init.d,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -r1.4 -r1.5 *** dnet-progs.init.d 21 Oct 2001 14:23:02 -0000 1.4 --- dnet-progs.init.d 17 Apr 2002 09:45:06 -0000 1.5 *************** *** 1,5 **** #!/bin/sh # ! # dnet-progs.sh # # Starts/stops DECnet processes --- 1,5 ---- #!/bin/sh # ! # dnet-progs.sh # # Starts/stops DECnet processes *************** *** 13,24 **** . /etc/default/decnet case $1 in start) - # Don't issue any messages if DECnet is not configured as - # dnet-common will have taken care of those. - if [ ! -f /etc/decnet.conf -o ! -f /proc/net/decnet ] - then - exit 1 - fi echo -n "Starting DECnet daemons:" --- 13,25 ---- . /etc/default/decnet + # Don't issue any messages if DECnet is not configured as + # dnet-common will have taken care of those. + if [ ! -f /etc/decnet.conf -o ! -f /proc/net/decnet ] + then + exit 1 + fi + case $1 in start) echo -n "Starting DECnet daemons:" *************** *** 29,33 **** then echo -n " $i" ! start-stop-daemon --start --quiet --exec /usr/sbin/$i fi done --- 30,34 ---- then echo -n " $i" ! start-stop-daemon --start --quiet --exec /usr/sbin/$i fi done |
From: Patrick C. <pa...@us...> - 2002-04-17 07:42:34
|
Update of /cvsroot/linux-decnet/dnprogs/apps In directory usw-pr-cvs1:/tmp/cvs-serv14114 Modified Files: dnping.c dnping.1 Log Message: Add support for timeout. Index: dnping.c =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/apps/dnping.c,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -r1.3 -r1.4 *** dnping.c 21 Oct 2001 14:24:00 -0000 1.3 --- dnping.c 17 Apr 2002 07:42:31 -0000 1.4 *************** *** 24,27 **** --- 24,28 ---- #include <stdlib.h> #include <ctype.h> + #include <signal.h> #include <sys/time.h> #include <sys/socket.h> *************** *** 38,41 **** --- 39,43 ---- #define DNF_DEBUG 0x080 #define DNF_TIMESTAMPS 0x100 + #define DNF_TIMEOUT 0x200 #define MIN(a,b) (((a) < (b)) ? (a) : (b)) *************** *** 66,69 **** --- 68,72 ---- printf("\t-u username access control username {}\n"); printf("\t-v verbose mode {OFF}\n"); + printf("\t-w seconds maximum wait time (timeout)\n"); exit(0); } *************** *** 160,163 **** --- 163,172 ---- } + void sig_alarm(int s) + { + printf("Connect timed out\n"); + exit(1); + } + /*-------------------------------------------------------------------------*/ int main(int argc, char *argv[]) *************** *** 166,174 **** struct accessdata_dn accessdata; static struct nodeent *np; char nodename[20], ibuf[MAX_DN_PACKETSIZE], obuf[MAX_DN_PACKETSIZE]; short snd,rcv,num; ! int sockfd,i,ch; char username[DN_MAXACCL],password[DN_MAXACCL]; int npackets = 10, --- 175,184 ---- struct accessdata_dn accessdata; static struct nodeent *np; + int sockfd,i,ch; char nodename[20], ibuf[MAX_DN_PACKETSIZE], obuf[MAX_DN_PACKETSIZE]; short snd,rcv,num; ! char username[DN_MAXACCL],password[DN_MAXACCL]; int npackets = 10, *************** *** 181,190 **** tmax = 0; /* maximum round trip time */ unsigned long tsum = 0; /* sum of all times, for doing average */ ! ! ! ! while ((ch = getopt(argc, argv, "c:di:qs:u:p:vt")) != EOF) { switch(ch) --- 191,200 ---- tmax = 0; /* maximum round trip time */ unsigned long tsum = 0; /* sum of all times, for doing average */ + unsigned long timeout_sec; + struct timeval timeout; + signal(SIGALRM, sig_alarm); ! while ((ch = getopt(argc, argv, "c:di:qs:u:p:w:vt")) != EOF) { switch(ch) *************** *** 242,247 **** --- 252,262 ---- snprintf(password,sizeof(password),"%s",optarg); break; + case 'w': + options |= DNF_TIMEOUT; + timeout_sec = atoi(optarg); + break; default: usage(); + break; } } *************** *** 336,339 **** --- 351,359 ---- memcpy(sockaddr.sdn_add.a_addr, np->n_addr,2); + /* This is the cheesy, cowards way of checking for + a connect timeout */ + if (options & DNF_TIMEOUT) + alarm(timeout_sec); + if (connect(sockfd, (struct sockaddr *)&sockaddr, sizeof(sockaddr)) < 0) *************** *** 346,349 **** --- 366,374 ---- } + /* Cancel the connect() alarm */ + if (options & DNF_TIMEOUT) + alarm(0); + + for (i = 0; i < datalen; i++) { *************** *** 389,392 **** --- 414,441 ---- snd++; + if (options & DNF_TIMEOUT) + { + int status; + fd_set in_fd; + + FD_ZERO(&in_fd); + FD_SET(sockfd, &in_fd); + timeout.tv_sec = timeout_sec; + timeout.tv_usec = 0; + + status = select(sockfd+1, &in_fd, NULL, NULL, &tv); + if (status < 0) + { + perror("select"); + close(sockfd); + exit(-1); + } + if (status == 0) + { + fprintf(stderr, "Timeout\n"); + close(sockfd); + exit(-1); + } + } num = read(sockfd,ibuf,sizeof(ibuf)); if ( num < 0 ) Index: dnping.1 =================================================================== RCS file: /cvsroot/linux-decnet/dnprogs/apps/dnping.1,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -r1.3 -r1.4 *** dnping.1 14 Mar 2001 19:41:36 -0000 1.3 --- dnping.1 17 Apr 2002 07:42:31 -0000 1.4 *************** *** 5,9 **** .SH SYNOPSIS ! .B dnping nodename [user pass] count .br --- 5,9 ---- .SH SYNOPSIS ! .B dnping nodename [user pass] count .br *************** *** 15,19 **** Options: .br ! [\dqsv] [\-c number] [\-i interval] [\-p password] [\-s size] [\-u username] .br .SH DESCRIPTION --- 15,19 ---- Options: .br ! [\dqsv] [\-c number] [\-i interval] [\-p password] [\-s size] [\-u username] [\-w timeout] .br .SH DESCRIPTION *************** *** 26,32 **** username and password may be specified for the connection as well as several other options. NOTE that if you dnping another Linux box it must ! have .B dnetd running. .SH OPTIONS --- 26,39 ---- username and password may be specified for the connection as well as several other options. NOTE that if you dnping another Linux box it must ! have .B dnetd running. + .br + NOTE also that dnping is not really like an IP "ping" in that it needs + a registered object at the other end to connect to. So, just because + you cannot ping a machine does not, necessarily, mean that machine + is not available, just that the MIRROR object is not available. There + is not (to my knowledge) a low-level equivalent in DECnet of the ICMP + ping message. .SH OPTIONS *************** *** 56,62 **** access control username .TP .I "-v" verbose mode (default off) ! .SH EXAMPLES .br --- 63,74 ---- access control username .TP + .I "-w timeout" + Specifies a timeout (in seconds). If not response is received + after this time then dnping will abort. The default is to wait + forever. + .TP .I "-v" verbose mode (default off) ! .SH EXAMPLES .br |
From: Patrick C. <pa...@us...> - 2002-04-05 10:07:08
|
Update of /cvsroot/linux-decnet/latd In directory usw-pr-cvs1:/tmp/cvs-serv3489 Modified Files: server.cc server.h Log Message: Use getloadavg() rather than /proc to get the load average. Index: server.cc =================================================================== RCS file: /cvsroot/linux-decnet/latd/server.cc,v retrieving revision 1.59 retrieving revision 1.60 diff -C2 -r1.59 -r1.60 *** server.cc 3 Apr 2002 15:40:30 -0000 1.59 --- server.cc 5 Apr 2002 10:07:04 -0000 1.60 *************** *** 734,751 **** /* Get the system load average */ ! float LATServer::get_loadavg(void) { ! float a,b,c; ! FILE *f = fopen("/proc/loadavg", "r"); ! if (!f) return 0; ! ! if (fscanf(f, "%g %g %g", &a, &b, &c) != 3) ! a = b = c = 0.0; ! ! fclose(f); ! ! return b; } --- 734,749 ---- /* Get the system load average */ ! double LATServer::get_loadavg(void) { ! double avg[3]; ! if (getloadavg(avg, 3) > 0) ! { ! return avg[0]; ! } ! else ! { return 0; ! } } Index: server.h =================================================================== RCS file: /cvsroot/linux-decnet/latd/server.h,v retrieving revision 1.36 retrieving revision 1.37 diff -C2 -r1.36 -r1.37 *** server.h 1 Mar 2002 14:19:34 -0000 1.36 --- server.h 5 Apr 2002 10:07:04 -0000 1.37 *************** *** 87,91 **** void read_lat(int sock); ! float get_loadavg(); void reply_to_enq(unsigned char *inbuf, int len, int interface, unsigned char *remote_mac); --- 87,91 ---- void read_lat(int sock); ! double get_loadavg(); void reply_to_enq(unsigned char *inbuf, int len, int interface, unsigned char *remote_mac); |
From: Patrick C. <pa...@us...> - 2002-04-03 15:40:38
|
Update of /cvsroot/linux-decnet/latd In directory usw-pr-cvs1:/tmp/cvs-serv28059 Modified Files: localport.cc server.cc services.cc Log Message: Use .width & .setf to set the width & format of iostreams so that they work correctly on gcc 3.0 and 2.95. Now I know why people really hate iostreams (and I've joined them). Index: localport.cc =================================================================== RCS file: /cvsroot/linux-decnet/latd/localport.cc,v retrieving revision 1.7 retrieving revision 1.8 diff -C2 -r1.7 -r1.8 *** localport.cc 13 Feb 2002 16:50:08 -0000 1.7 --- localport.cc 3 Apr 2002 15:40:30 -0000 1.8 *************** *** 222,229 **** void LocalPort::show_info(bool verbose, std::ostrstream &output) { ! output << devname << std::setw(24-devname.length()) << " " << service ! << std::setw(16-service.length()) << " " ! << remnode << std::setw(16-remnode.length()) << " " << portname ! << std::setw(16-portname.length()) << " " << (queued?"Yes":"No ") ! << (clean?" 8":" ") << std::endl; } --- 222,237 ---- void LocalPort::show_info(bool verbose, std::ostrstream &output) { ! output.setf(std::ios::left, std::ios::adjustfield); ! ! output.width(23); ! output << devname.c_str() << " "; ! ! output.width(15); ! output << service.c_str() << " "; ! ! output.width(15); ! output << remnode.c_str() << " "; ! ! output.width(15); ! output << portname.c_str() << " " << (queued?"Yes":"No ") << (clean?" 8":" ") << std::endl; } Index: server.cc =================================================================== RCS file: /cvsroot/linux-decnet/latd/server.cc,v retrieving revision 1.58 retrieving revision 1.59 diff -C2 -r1.58 -r1.59 *** server.cc 7 Mar 2002 11:49:28 -0000 1.58 --- server.cc 3 Apr 2002 15:40:30 -0000 1.59 *************** *** 1556,1560 **** { output <<std::endl; ! output << "Node Name: " << get_local_node() << std::setw(16-strlen((char*)get_local_node())) << " " << " LAT Protocol Version: " << LAT_VERSION << "." << LAT_VERSION_ECO << std::endl; output << "Node State: On " << " LATD Version: " << VERSION << std::endl; output << "Node Ident: " << greeting << std::endl; --- 1556,1565 ---- { output <<std::endl; ! output.setf(std::ios::left, std::ios::adjustfield); ! ! output << "Node Name: "; ! output.width(15); ! output << get_local_node() << " " << " LAT Protocol Version: " << LAT_VERSION << "." << LAT_VERSION_ECO << std::endl; ! output.setf(std::ios::right, std::ios::adjustfield); output << "Node State: On " << " LATD Version: " << VERSION << std::endl; output << "Node Ident: " << greeting << std::endl; *************** *** 1586,1590 **** for (; i != servicelist.end(); i++) { ! output << std::setw(16) << i->get_name() << std::setw(15-i->get_name().size()) << " " << "Enabled" << std::setw(6) << i->get_rating() << (i->get_static()?" ":" D ") << i->get_id() << std::endl; } --- 1591,1599 ---- for (; i != servicelist.end(); i++) { ! output.width(15); ! output.setf(std::ios::left, std::ios::adjustfield); ! output << i->get_name().c_str(); ! output.setf(std::ios::right, std::ios::adjustfield); ! output << "Enabled" << std::setw(6) << i->get_rating() << (i->get_static()?" ":" D ") << i->get_id() << std::endl; } Index: services.cc =================================================================== RCS file: /cvsroot/linux-decnet/latd/services.cc,v retrieving revision 1.10 retrieving revision 1.11 diff -C2 -r1.10 -r1.11 *** services.cc 13 Feb 2002 16:59:13 -0000 1.10 --- services.cc 3 Apr 2002 15:40:30 -0000 1.11 *************** *** 171,178 **** for (; n != nodes.end(); n++) { ! output << std::setw(28 - n->first.length()) << n->first << ! (nodes[n->first].is_available()?"Reachable ":"Unreachable") << " " << ! std::setw(4) << nodes[n->first].get_rating() << " " << ! nodes[n->first].get_ident() << std::endl; } } --- 171,182 ---- for (; n != nodes.end(); n++) { ! output.width(17); ! output.setf(std::ios::left, std::ios::adjustfield); ! output << n->first.c_str() << ! (nodes[n->first].is_available()?"Reachable ":"Unreachable") << " "; ! output.width(4); ! output.setf(std::ios::right, std::ios::adjustfield); ! output << nodes[n->first].get_rating() << " " << ! nodes[n->first].get_ident() << std::endl; } } *************** *** 194,198 **** output << "Service Status: " << (servicelist[s->first].is_available()?"Available ":"Unavailable") << " " << std::endl; output << "Service Ident: " << servicelist[s->first].get_ident() << std::endl << std::endl; ! servicelist[s->first].list_service(output); output << "--------------------------------------------------------------------------------" << std::endl; --- 198,202 ---- output << "Service Status: " << (servicelist[s->first].is_available()?"Available ":"Unavailable") << " " << std::endl; output << "Service Ident: " << servicelist[s->first].get_ident() << std::endl << std::endl; ! servicelist[s->first].list_service(output); output << "--------------------------------------------------------------------------------" << std::endl; *************** *** 200,206 **** else { ! output << std::setw(28 - s->first.length()) << s->first << ! (servicelist[s->first].is_available()?"Available ":"Unavailable") << " " << ! servicelist[s->first].get_ident() << std::endl; } } --- 204,211 ---- else { ! output.width(28); ! output.setf(std::ios::left, std::ios::adjustfield); ! output << s->first.c_str() << (servicelist[s->first].is_available()?"Available ":"Unavailable") << " " << ! servicelist[s->first].get_ident() << std::endl; } } |
From: Patrick C. <pa...@us...> - 2002-04-03 13:59:02
|
Update of /cvsroot/linux-decnet/latd/debian In directory usw-pr-cvs1:/tmp/cvs-serv26589/debian Modified Files: rules Log Message: dh_testversion is deprecated so remove it. Index: rules =================================================================== RCS file: /cvsroot/linux-decnet/latd/debian/rules,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -r1.3 -r1.4 *** rules 12 Feb 2001 15:27:25 -0000 1.3 --- rules 3 Apr 2002 13:41:49 -0000 1.4 *************** *** 32,36 **** make install DESTDIR=`pwd`/debian/tmp RELEASE=true mv debian/tmp/usr/man debian/tmp/usr/share - dh_testversion 2 dh_installdirs dh_installchangelogs --- 32,35 ---- |
From: Patrick C. <pa...@us...> - 2002-04-03 13:40:53
|
Update of /cvsroot/linux-decnet/latd In directory usw-pr-cvs1:/tmp/cvs-serv26443 Modified Files: lat.html Log Message: Missing space. Index: lat.html =================================================================== RCS file: /cvsroot/linux-decnet/latd/lat.html,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -r1.3 -r1.4 *** lat.html 9 Mar 2002 17:07:24 -0000 1.3 --- lat.html 3 Apr 2002 13:40:46 -0000 1.4 *************** *** 16,20 **** <p><font size="+3">A project to provide DECnet phase IV connectivity ! forLinux</font><br> </p> --- 16,20 ---- <p><font size="+3">A project to provide DECnet phase IV connectivity ! for Linux</font><br> </p> |
From: Patrick C. <pa...@us...> - 2002-04-03 13:40:42
|
Update of /cvsroot/linux-decnet/latd In directory usw-pr-cvs1:/tmp/cvs-serv26360 Modified Files: latcp.cc Log Message: Get rid of Linux-specific code. Index: latcp.cc =================================================================== RCS file: /cvsroot/linux-decnet/latd/latcp.cc,v retrieving revision 1.33 retrieving revision 1.34 diff -C2 -r1.33 -r1.34 *** latcp.cc 3 Mar 2002 12:58:06 -0000 1.33 --- latcp.cc 3 Apr 2002 13:40:32 -0000 1.34 *************** *** 1,4 **** /****************************************************************************** ! (c) 2000-2001 Patrick Caulfield pa...@de... This program is free software; you can redistribute it and/or modify --- 1,4 ---- /****************************************************************************** ! (c) 2000-2002 Patrick Caulfield pa...@de... This program is free software; you can redistribute it and/or modify *************** *** 772,775 **** --- 772,776 ---- } } + // Otherwise look in some well-known places else if (!stat("/usr/sbin/latd", &st)) *************** *** 790,811 **** char *newenv[4]; int i; - char latcp_proc[PATH_MAX]; char latcp_bin[PATH_MAX]; char latcp_env[PATH_MAX+7]; ! // This is VERY Linux specific and needs /proc mounted. ! // we get the full path of the current executable by doing a readlink. ! // /proc/<pid>/exe ! ! #ifdef __linux__ ! sprintf(latcp_proc, "/proc/%d/exe", getpid()); ! if ( (i=readlink(latcp_proc, latcp_bin, sizeof(latcp_bin))) == -1) ! { ! fprintf(stderr, "readlink in /proc failed. Make sure the the proc filesystem is mounted on /proc\n"); ! exit(2); ! } ! #else ! #error OK, a bit more porting work needed here too. ! #endif sprintf(latcp_env, "LATCP=%s", latcp_bin); --- 791,799 ---- char *newenv[4]; int i; char latcp_bin[PATH_MAX]; char latcp_env[PATH_MAX+7]; ! realpath(argv[0], latcp_bin); ! sprintf(latcp_env, "LATCP=%s", latcp_bin); |