/***
*  poke.c
*  Usage: poke [-c] file location [value]	
* or	: poke [-c ] file loc val loc val ....
* -c mean: value are chars, not decimal
*  for mulinux
* Michele Andreoli (C) 2000 - Public Domain 
***/

#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdlib.h>

int WriteByte(char);
int WriteStr(int,char*);

#define BUFSIZE 1024 

int opt_c=0;

int err(char *msg)
{
printf ("poke: error %s\n",msg);
exit(1);
}


int usage()
{
printf ("poke.c (C) 2000 M.Andreoli\n");
printf ("Usage:\n\tpoke [opt] file location \t\t\t print loc value\n");
printf ("or\tpoke [opt] file loc val loc val ... \t\t set loc to val\n");
printf ("If opt=-c val are string\n");
printf ("Examples:\n");
printf ("\tpoke file 5 65 6 66\n");
printf ("\tpoke file -c 5 A 6 B\n");
printf ("\tpoke file -c 5 AB\n");
printf ("are equivalents.\n");
exit(0);
}

int main(int argc, char *argv[])

{
  char buf[BUFSIZE];
  int fd=0;
  int loc;
  char c;
  int n;
  char *filename;
  char opt=0;

/* syntax */

n=1;
if (  n > argc - 1 ) usage();

if ( argv[1][0] == '-' )
	{
	opt=argv[1][1];
	n++;
	}


switch ( opt )
{
case 'c': opt_c=1;
} 

if (  n > argc - 1 ) usage();
filename=argv[n];

fd=open(filename, O_RDWR);
if (fd <= 0 ) err("opening file");

n++;
if (  n > argc - 1 ) usage();

for ( ; n < argc; n=n+2 )
{
loc=atoi(argv[n])-1;
lseek(fd, loc, SEEK_SET); 

if ( argv[n+1] != NULL ) {
	WriteStr(fd, argv[n+1]);
} else {
	read(fd,&c,1);
	WriteByte(c);
}	
}	
  close(fd); 
  return 0;
}


int WriteStr(int f, char* p)
{
int value;
if (  opt_c == 0 ) {
	value= atoi( p );
	write(f,&value,1);
} else {
	write (f,p,strlen(p));
	}
}

int WriteByte(char c)
{
if (  opt_c ) {
	printf("%c",c);
} else {
	printf("%d",c);
	}
}
