/*
 * TITLE: touch.c
 * This is a simple command to set the date of a file to now.
 * It was compiled using Greenhills C.  You might have to change it
 * a little for use with Lattice or Manx.
 * The program compiles with just amigalib.  (that's why those string
 * functions are tacked on the end of the file)
 */
 
/* touch.c by Phil Lindsay and Andy Finkel              */
/* (c) 1986 Commodore-Amiga, Inc.                       */
/* Permission to use in any way granted, as long as     */
/* the copyright notice stays intact                    */

#include "exec/types.h"
#include "exec/ports.h"
#include "exec/io.h"
#include "exec/memory.h"
#include "libraries/dos.h"
#include "libraries/dosextens.h"

extern LONG sendpkt();
static void strcpy();
static int strlen();

#define ACTION_SET_DATE     34
#define DOSTRUE             -1

int main(argc,argv)
int argc;
char *argv[];
{
 struct MsgPort *task;
 LONG arg[4];
 LONG rc;
 ULONG dateStamp[3];
 ULONG lock;
 ULONG plock;
 UBYTE *pointer;
 void cleanup ();

pointer=NULL;
if(argc!=2) {
        puts("Bad argument\n");
        cleanup(pointer,20);
}

if( !(pointer= (UBYTE *)AllocMem(64,MEMF_PUBLIC)))cleanup(pointer,20);
if(!(task=(struct MsgPort *)DeviceProc(argv[1])))cleanup(pointer,20);
if(!(lock = (ULONG) Lock(argv[1],SHARED_LOCK)))cleanup(pointer,20);
plock = (ULONG) ParentDir(lock);
UnLock(lock);

strcpy((pointer + 1),argv[1]);
*pointer = strlen(argv[1]);
 
arg[0]= NULL;
arg[1]= plock;
arg[2]= (ULONG) &pointer[0] >> 2;                /* BSTR of filename */
arg[3]= (ULONG) DateStamp(dateStamp);            /* DateStamp */
rc = sendpkt(task,ACTION_SET_DATE,arg,4);

UnLock(plock);
if(!rc) cleanup(pointer,20);  
cleanup(pointer,0); 
return (0);
}

void cleanup(pointer,code)
UBYTE *pointer;
LONG code;
{
if(pointer)FreeMem(pointer,64);
exit(code);
}

LONG 
sendpkt(id,type,args,nargs)
struct MsgPort *id;     /* process indentifier ... (handlers message port ) */
LONG type,           /* packet type ... (what you want handler to do )   */
     args[],          /* a pointer to a argument list */
     nargs;          /* number of arguments in list  */
{
  
 struct MsgPort        *replyport;
 struct StandardPacket *packet = NULL;
 
 LONG   count, *pargs, res1=NULL; 


if(!(replyport = (struct MsgPort *) CreatePort(NULL,NULL)))return(NULL);

packet=(struct StandardPacket *)
        AllocMem((LONG)sizeof(*packet),MEMF_PUBLIC|MEMF_CLEAR);

if(packet) {
    packet->sp_Msg.mn_Node.ln_Name = (char *) &(packet->sp_Pkt); /*link packet */
    packet->sp_Pkt.dp_Link = &(packet->sp_Msg);        /* to message    */
    packet->sp_Pkt.dp_Port = replyport;         /* set-up reply port   */
    packet->sp_Pkt.dp_Type = type;           /* what to do... */

    /* move all the arguments to the packet */
    pargs = &(packet->sp_Pkt.dp_Arg1); /* address of first argument */
    for(count=0; (count < nargs) && (count < 7); count++)pargs[count]=args[count
];

    PutMsg(id,packet); /* send packet */
    WaitPort(replyport); /* wait for packet to come back */
    GetMsg(replyport);   /* pull message */

    res1 = packet->sp_Pkt.dp_Res1; /* get result */

}
FreeMem(packet,(LONG)sizeof(*packet)); 
DeletePort(replyport); 
return(res1);   
  
}

static void
strcpy( to, from )
register char *to, *from;
{
    do {
        *to++ = *from;
    } while( *from++ );
}

static int
strlen( s )
register char *s;
{
    register i = 0;

    while( *s++ ) i++;

    return( i );
}
