home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Columbia Kermit
/
kermit.zip
/
pub
/
uniflex
/
ufkerm.uue
/
ufkerm.arc
/
UFATTR.C
next >
Wrap
C/C++ Source or Header
|
1989-01-09
|
9KB
|
292 lines
/*
Kermit's attribute packets services
*/
#include "ufk.h"
#include <stat.h>
#include <time.h>
#include <timeb.h>
#define leap(y) (!(y & 3)) /* Return TRUE if it's a leap year */
unsigned int perms,
operms;
int owner;
struct tm timbuf;
char opsys[3];
init_attributes()
{
file_size = 0; /* for % display, remains 0 if none */
perms = 0xffff; /* 'world' permissions */
operms = 0xffff; /* permissions in our syntax */
timbuf.tm_yday = -1; /* no date given yet */
}
snd_attributes()
{
struct stat buf;
struct tm *localtime();
struct tm *tpt;
int locfp;
char *p,
hlpstr[16];
unsigned char filechar;
locfp = open(filnam,0);
fstat(locfp,&buf); /* filnam is already verified */
p = sndpkt;
/* setup system of origin. Define UniFLEX to be number 'UF' */
addstr('.',&p,"UF");
/* setup file size in blocks */
sprintf(hlpstr,"%d",(int)((buf.st_size + 1024l) / 1024l));/* Rounded in K */
addstr('!',&p,hlpstr);
/* setup file size in bytes */
sprintf(hlpstr,"%ld",buf.st_size);
addstr('1',&p,hlpstr);
/* setup creation date */
tpt = localtime(&buf.st_mtime);
sprintf(hlpstr,"%02.2d%02.2d%02.2d %02.2d:%02.2d:%02.2d",
tpt->tm_year, tpt->tm_mon + 1, tpt->tm_mday,
tpt->tm_hour, tpt->tm_min, tpt->tm_secs);
addstr('#',&p,hlpstr);
/* setup file protection with respect to the world */
*p++ = '-';
*p++ = tochar(1);
*p++ = tochar((buf.st_mode & S_IPRM) >> 3);
/* setup file protection in our syntax */
*p++ = ',';
*p++ = tochar(2);
*p++ = tochar((buf.st_mode & S_IPRM) & 0x0f);
*p++ = tochar((buf.st_mode & S_IPRM) >> 4);
/* setup file owner */
sprintf(hlpstr,"%d",buf.st_uid);
addstr('$',&p,hlpstr);
/* set file type */
*p++ = '"';
*p++ = tochar(1);
read(locfp,&filechar,1);
if ((filechar <= 0x09) ||
(filechar > 0x7e))
{
binfil = TRUE; /* Binary file */
*p++ = 'B';
}
else
{
binfil = FALSE; /* Ascii file */
*p++ = 'A';
}
*p = '\0';
size = p - sndpkt; /* Final packet size */
close (locfp);
}
rcv_attributes()
{
int len,
filesize;
long dsize;
char *p,
*q,
*r,
*pos,
hlpstr[10],
type,
*index(),
*rindex();
p = recpkt;
while (p < recpkt + size)
{
type = *p++;
if ((len = unchar(*p++)) != 0)
{
switch(type)
{
case '.': /* operating system origin */
strncpy(opsys,p,len);
opsys[len] = '\0';
break;
case '!': /* Filesize in K bytes */
strncpy(hlpstr,p,len);
hlpstr[len] = '\0';
sscanf(hlpstr,"%d",&filesize);
pos = rindex(rec_filnam,'/');
if (pos == NULL)
strcpy(hlpstr,".");
else
{
strncpy(hlpstr,rec_filnam,pos - rec_filnam);
hlpstr[pos-rec_filnam] = '\0';
}
dsize = get_free(hlpstr); /* Get number of free blocks */
if ((dsize == -1l) ||
(dsize < (long)filesize))
return(ERROR); /* File too big to fit */
break;
case '1': /* Number of bytes in file */
strncpy(hlpstr,p,len);
hlpstr[len] = '\0';
sscanf(hlpstr,"%ld",&file_size);
break;
case '"': /* File type */
type = *p;
if (type == 'A')
binfil = FALSE; /* Ascii */
else if (type == 'B')
binfil = TRUE; /* Binary */
break;
case '-': /* File permissions */
perms = unchar(*p) & 7;
break;
case ',': /* File permissions in our syntax */
operms = unchar(p[0]);
if (len > 1)
operms |= (unchar(p[1]) << 4);
break;
case '$': /* File owner */
strncpy(hlpstr,p,len);
hlpstr[len] = '\0';
sscanf(hlpstr,"%d",&owner);
break;
case '#': /* File date */
q = p; /* Check if date and time specified */
if (len > 8)
{ /* both date and time */
r = index(p,' ');
if ((r - p) == 8)
q = &p[2]; /* skip first two digits of date */
}
else if (len == 8) /* only date specified */
q = &p[2];
timbuf.tm_hour = 0; /* Zero out optional items */
timbuf.tm_min = 0;
timbuf.tm_secs = 0;
sscanf(q,"%2d%2d%2d %d:%d:%d",
&timbuf.tm_year,
&timbuf.tm_mon,
&timbuf.tm_mday,
&timbuf.tm_hour,
&timbuf.tm_min,
&timbuf.tm_secs);
timbuf.tm_mon--; /* Adjust month */
timbuf.tm_yday = 0; /* Flag date given */
break;
default:
break;
}
}
p += len;
}
return NULL;
}
fset_attributes()
{
long cvttime();
struct stat buf;
if (stat(rec_filnam,&buf)) /* Get status of current filename */
prterr(ER_PERMS);
else
{
if (perms != 0xffff)
{ /* 'world' syntax */
perms = (buf.st_mode &
S_IPRM & /* Mask for permissions */
~(S_IOREAD | S_IOWRITE | S_IOEXEC)) |
(perms << 3); /* set new 'other' bits */
if (chmod(rec_filnam,perms) == ERROR)
prterr(ER_PERMS);
}
if ((operms != 0xffff) &&
(strcmp(opsys,"UF") == 0)) /* 'our' syntax */
if (chmod(rec_filnam,operms) == ERROR)
prterr(ER_PERMS);
}
if (timbuf.tm_yday != -1)
fset_date(rec_filnam,cvttime(&timbuf)); /* Set new date */
}
addstr(type,q,string)
char type,
**q,
*string;
{
int length;
length = strlen(string);
*(*q)++ = type;
*(*q)++ = tochar(length);
strcpy(*q,string);
*q += length;
}
long cvttime(buf)
struct tm *buf;
{
struct timeb tbuf; /* To read the timezone */
static char daytab[] = { /* Number of days for each month */
31, 28, 31, 30,
31, 30, 31, 31,
30, 31, 30, 31
};
int days_so_far,
i,
j;
long int sec_sin_80; /* Accumulated number of seconds */
days_so_far = 0;
for (j = 80; j < buf->tm_year; j++)/* Calc number of days for past years */
{
for (i = 0; i < 12; i++)
days_so_far += daytab[i]; /* Add number of days in a year */
if (leap(j))
days_so_far++; /* one more in a leap year */
}
for (i = 0; i < buf->tm_mon; i++)/* Calc number of days for past months */
{
days_so_far += daytab[i];
if ((i == 1) && leap(buf->tm_year))
days_so_far++; /* Take care of 29 februari */
}
days_so_far += buf->tm_mday - 1; /* Add number of days this month */
sec_sin_80 = ((long)buf->tm_hour * 3600) +
(buf->tm_min * 60) +
buf->tm_secs;
sec_sin_80 += days_so_far * (long) 86400;
ftime(&tbuf); /* Get timezone value */
sec_sin_80 += tbuf.timezone * 60; /* Correct for it */
return(sec_sin_80); /* That's it, return the time */
}