Hello everybody,

here's my patch and the corresponding code for AVR.

I use bit-banging as to save the slave select pin, which I need otherwise.
For low datarates it should be no problem to have 2 interrupts per bit.


Please tell me if you have hints or corrections!

Thank you for uisp!


Regards,

Phil
=== src/AvrDummy.C
==================================================================
--- src/AvrDummy.C	(revision 8)
+++ src/AvrDummy.C	(revision 20)
@@ -622,7 +622,7 @@
   /* Device Command line options ... */ 
   if (GetCmdParam("-dno-poll", false)){use_data_polling=false;} 
   
-  EnableAvr();
+  if (!GetCmdParam("-dno-enable", false)) EnableAvr();
 }
 
 #endif
=== src/DAPA.h
==================================================================
--- src/DAPA.h	(revision 8)
+++ src/DAPA.h	(revision 20)
@@ -69,7 +69,6 @@
 private:
   int SendRecv(int);
   /* low level access to parallel port lines */
-  void OutReset(int);
   void OutSck(int);
   void OutData(int);
   void SckDelay();
@@ -89,6 +88,7 @@
   /* If enable command 0x53 did not echo back, give a positive SCK
      pulse and retry again.
   */
+  void OutReset(int);
   void PulseSck();
   void PulseReset();
   void Init();
=== src/Main.C
==================================================================
--- src/Main.C	(revision 8)
+++ src/Main.C	(revision 20)
@@ -36,6 +36,8 @@
 #include <stdarg.h>
 #include <stdlib.h>
 #include <string.h>
+#include <ctype.h>
+#include <signal.h>
 #include "Terminal.h"
 #include "MotIntl.h"
 #include "AvrAtmel.h"
@@ -56,6 +58,8 @@
 TMotIntl motintl;
 TTerminal terminal;
 
+volatile int quit=0;
+
 const char* version = "uisp version %s\n"
 "(C) 1997-1999 Uros Platise, 2000-2003 Marek Michalkiewicz\n"
 "\nuisp is free software, covered by the GNU General Public License.\n"
@@ -230,6 +234,12 @@
 }
 
 
+void SigHandler(int sig)
+{
+	quit=1;
+}
+
+
 int main(int _argc, const char* _argv[]){
   int return_val=0;
   argc = _argc;
@@ -288,7 +298,79 @@
 #ifndef NO_DAPA
     else if (val) {
       /* The TDAPA() constructor will drop setuid privileges after
-         opening the lpt ioport. */
+	 opening the lpt ioport. */
+      if (GetCmdParam("--console", false))
+      {
+	unsigned char buffer[16];
+	fd_set set;
+	struct timeval tv;
+	int l,i;
+	TDAPA *ad=new TDAPA;
+	struct termios tios, tios2;
+	int hex_out;
+
+
+	signal(SIGQUIT, SigHandler);
+	signal(SIGINT, SigHandler);
+	signal(SIGTERM, SigHandler);
+	signal(SIGPIPE, SigHandler);
+
+	hex_out=!!GetCmdParam("--hex-out", false);
+
+	printf("Connection established.\n");
+	if (tcgetattr(0, &tios) == -1)
+	  throw Error_Device("Cannot get terminal attributes");
+	memcpy(&tios2, &tios, sizeof(tios));
+	tios2.c_cc[VMIN]=0;
+	tios2.c_lflag &= ~(ICANON | ECHO);
+	if (tcsetattr(0, TCSANOW, &tios2) == -1)
+	  throw Error_Device("Cannot get terminal attributes");
+	ad->OutReset(1);
+
+	while(!quit)
+	{
+	  FD_ZERO(&set);
+	  FD_SET(0,&set);
+	  tv.tv_sec=0;
+	  tv.tv_usec=100000;
+	  if (select(1,&set, NULL,NULL, &tv))
+	  {
+	    l=read(0, buffer+1, sizeof(buffer)-1);
+	    if (l <= 0) break;
+	  }
+	  else
+	    l=0;
+
+	  buffer[0]=0x7f;
+	  ad->Send(buffer, l+1, sizeof(buffer));
+	  for(i=0; i<l+1; i++)
+	  {
+	    switch (buffer[i])
+	    {
+	      case 0:
+		break;
+	      default:
+		if (hex_out)
+		{
+		  printf("'%c' = hex %02X = dez %d = bin ",
+		      isprint(buffer[i]) ? buffer[i] : ' ',
+		      buffer[i], buffer[i]);
+		  for(l=7; l>=0; l--) putchar((buffer[i] & (1 << l)) ? '1' : '0');
+		  putchar('\n');
+		}
+		else
+		  putchar(buffer[i]);
+	    }
+	  }
+
+	  fflush(stdout);
+	}
+
+	if (tcsetattr(0, TCSANOW, &tios) == -1)
+	  throw Error_Device("Cannot get terminal attributes");
+	return 0;
+      }
+
       device = new TAvrDummy();
     }
 #endif
@@ -296,7 +378,7 @@
     /* Check Device's bad command line params. */
     for (int i=1; i<argc; i++){
       if (argv_ok[i]==0 && strncmp(argv[i], "-d", 2)==0){
-        Info(0,"Invalid parameter: %s\n", argv[i]); exit(1);
+	Info(0,"Invalid parameter: %s\n", argv[i]); exit(1);
       }
     }    
     if (device()==NULL){
@@ -310,7 +392,7 @@
       }
     }
 
-    	/* Device Operations: */
+    /* Device Operations: */
 
     if (GetCmdParam("--download", false)) {
       motintl.Write(GetCmdParam("of"));
@@ -335,7 +417,7 @@
       printf("Fuse High Byte     = 0x%02x\n", device->ReadByte(AVR_FUSE_HIGH_ADDR));
       printf("Fuse Extended Byte = 0x%02x\n", device->ReadByte(AVR_FUSE_EXT_ADDR));
       printf("Calibration Byte   = 0x%02x  --  Read Only\n",
-             device->ReadByte(AVR_CAL_ADDR));
+	  device->ReadByte(AVR_CAL_ADDR));
 
       bits = device->ReadByte(AVR_LOCK_ADDR);
       printf("Lock Bits          = 0x%02x\n", bits);
@@ -359,11 +441,11 @@
 
       if (sscanf(val, "%x", &bits) == 1)
       {
-        device->WriteByte( AVR_FUSE_LOW_ADDR, (TByte)bits );
-        printf("\nFuse Low Byte set to 0x%02x\n", (TByte)bits);
+	device->WriteByte( AVR_FUSE_LOW_ADDR, (TByte)bits );
+	printf("\nFuse Low Byte set to 0x%02x\n", (TByte)bits);
       }
       else
-        throw Error_Device("Invalid argument for --wr_fuse_l.");
+	throw Error_Device("Invalid argument for --wr_fuse_l.");
 
       device->SetSegment(old_seg);
     }
@@ -376,11 +458,11 @@
 
       if (sscanf(val, "%x", &bits) == 1)
       {
-        device->WriteByte( AVR_FUSE_HIGH_ADDR, (TByte)bits );
-        printf("\nFuse High Byte set to 0x%02x\n", (TByte)bits);
+	device->WriteByte( AVR_FUSE_HIGH_ADDR, (TByte)bits );
+	printf("\nFuse High Byte set to 0x%02x\n", (TByte)bits);
       }
       else
-        throw Error_Device("Invalid argument for --wr_fuse_h.");
+	throw Error_Device("Invalid argument for --wr_fuse_h.");
 
       device->SetSegment(old_seg);
     }
@@ -393,11 +475,11 @@
 
       if (sscanf(val, "%x", &bits) == 1)
       {
-        device->WriteByte( AVR_FUSE_EXT_ADDR, (TByte)bits );
-        printf("\nFuse Extended Byte set to 0x%02x\n", (TByte)bits);
+	device->WriteByte( AVR_FUSE_EXT_ADDR, (TByte)bits );
+	printf("\nFuse Extended Byte set to 0x%02x\n", (TByte)bits);
       }
       else
-        throw Error_Device("Invalid argument for --wr_fuse_e.");
+	throw Error_Device("Invalid argument for --wr_fuse_e.");
 
       device->SetSegment(old_seg);
     }
@@ -408,11 +490,11 @@
 
       if (sscanf(val, "%x", &bits) == 1)
       {
-        device->WriteLockBits( (TByte)bits );
-        printf("\nLock Bits set to 0x%02x\n", (TByte)bits);
+	device->WriteLockBits( (TByte)bits );
+	printf("\nLock Bits set to 0x%02x\n", (TByte)bits);
       }
       else
-        throw Error_Device("Invalid argument for --wr_lock.");
+	throw Error_Device("Invalid argument for --wr_lock.");
     }
 
     if (GetCmdParam("--lock", false))
@@ -422,10 +504,10 @@
       printf("\nLock Bits set to 0x%02x\n", 0xfc);
     }
 
-    	/* enter terminal */ 
-	
+    /* enter terminal */ 
+
     if (GetCmdParam("--terminal", false)){terminal.Run();}
-    
+
     /* Check bad command line parameters */
     for (int i=1; i<argc; i++){
       if (argv_ok[i]==0){Info(0,"Invalid parameter: %s\n", argv[i]);}
#ifndef __COMMUNICATION_PROGRAMMER__
#define __COMMUNICATION_PROGRAMMER__


#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/sleep.h>
#include <avr/signal.h>


#define SCK PB5
/* AVR writes at L->H; programmer reads at H->L */
#define MISO PB4

/* AVR reads on L->H; doc page 299 */
#define MOSI PB3

unsigned char out_buf[64],
	out_buf_cur=0, // current byte, >= 0
	out_buf_end=0, // number of bytes to send, >= 1

	cur_bit, // 7 .. 0

	overflow,

	inp_buf[64],
	inp_buf_cur, // current byte to recv
	inp_buf_read; // last used byte


SIGNAL(SIG_PIN_CHANGE0)
{
	static unsigned char cur_out, pins, tmp, cur_in;

	pins=PINB; 

	/* if SCK now high, read and/or write */
	if (pins & _BV(SCK))
	{
		/* read. MSB is first. */
		cur_in= ( cur_in << 1) | ((pins & _BV(MOSI)) ? 1 : 0);


		/* sending */
		tmp=0;
		if (overflow)
		{
			tmp=1;
			overflow--;
		}
		else
		{
			/* next byte ? */
			if (cur_bit == 0)
			{
				if (out_buf_cur < out_buf_end)
				{
					cur_out=out_buf[out_buf_cur];

					out_buf_cur++;
					if (out_buf_cur == out_buf_end)
						out_buf_end=out_buf_cur=0;
				}
				PORTB = PORTB ^ _BV(PB6);
			}

			/* MSB first */
			tmp = cur_out & 0x80;
			cur_out = cur_out << 1;
		}
		/* put on port */
		if (tmp)
			PORTB |= _BV(MISO);
		else
			PORTB &= ~_BV(MISO);


		/* next bits */
		cur_bit++;
		/* if we have a 0x7f in cur_in, we're in a resync phase.
		 * so assume that we're now synchronized. */
		if (cur_in == 0x7f) 
		{ 
			cur_bit=0;
		}
		if (cur_bit>=8)
		{
			cur_bit=0;
			/* full byte received.
			 * 0x00 ... ignored
			 * 0x7f ... sync byte. should be given multiple times.
			 * 0xbf, 0xdf, 0xef, 0xf7, 0xfb, 0xfd, 0xfe 
			 *          used for re-synchronisation. */
			switch (cur_in)
			{
				case 0:
					break; /* just ignored */
				default:
					inp_buf[inp_buf_cur]=cur_in;
					inp_buf_cur++;
					break;
			}
				PORTB = PORTB ^ _BV(PB7);
		}

		if (inp_buf_cur>sizeof(inp_buf)) 
		{
			/* if input buffer is overrun, input is discarded and 
			 * a number of 0xff bytes is written out.
			 * only zeroes should be given until this is finished. */
			overflow= 8*10; // multiple of 8 !!! 
			inp_buf_cur=0;
		}
	}

	return;
}


void io_init(void)
{
	/* enable MISO as output; SCK, MOSI as input. No pull-ups. */
	DDRB = ( DDRB & ~(_BV(MOSI) | _BV(SCK)) ) | _BV(MISO);
	PORTB &= ~(_BV(MISO) | _BV(MOSI) | _BV(SCK));

	PCMSK0|=_BV(SCK) | _BV(PB1);
	PCICR|=_BV(PCIE0);
	PCIFR=0xff;
}


inline char output_buffer_empty(void)
{
	return out_buf_end == 0;
}


inline void set_output_buffer(char len)
{
	out_buf_end=len;
}


char read_byte(void)
{
	char ret;

	if (inp_buf_read == inp_buf_cur) return 0;

	cli();
	ret=inp_buf[inp_buf_read++];
	if (inp_buf_read == inp_buf_cur) 
		inp_buf_cur=inp_buf_read=0;
	sei();

	return ret;
}



inline char look_last_byte(void)
{
	if (inp_buf_read == inp_buf_cur) return 0;

	return inp_buf[inp_buf_cur-1];
}


void write_byte(char x)
{
	if (out_buf_end >= sizeof(out_buf)-1) return;

	cli();
	out_buf[out_buf_end]=x;
	out_buf_end++;
	sei();
}


#endif

// vi: sw=3 ts=3 
_______________________________________________
Uisp-dev mailing list
Uisp-dev@nongnu.org
http://lists.nongnu.org/mailman/listinfo/uisp-dev

Reply via email to