⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 codeavr.c

📁 Outputs messages to a 2line LCD
💻 C
📖 第 1 页 / 共 4 页
字号:
}


// divide the primary register by INTSIZE

void gasrint(void) {
	ol("lsr\tr31");
	ol("ror\tr30");
}


// Case jump instruction

void gjcase(void) {
//	addglb("_case", 0, 0, 0, 0, 0);
//	ptr = findglb("_case");
//   symtab[ptr].used = 1;
	if (!CheckExtFun("_case"))
	  	ol("extern\t_case");
	ot("rjmp\t_case");
	nl();
}


// Add the primary and secondary registers

void gadd(int type) {
//	if (stkptr == 0) {
//   	if (type < 0)
//			gpop(CINT);
//		else
			gpop(type);
//    	}
   if (type == CLONG) {
   	gcall("add_l", CINT);
      }
   else {
		ol("add\tr26,r30");
//      if (type < 0 || type == CINT)
			ol("adc\tr27,r31");
      InX = 1;
      }
}


// Subtract the primary register from the secondary.
// Move answer to primary.

void gsub(int type) {
	gpop(type);
   if (type == CLONG)
   	gcall("sub_l", CINT);
   else {
   	if (InX) {
			ol("sub\tr26,r30");
     		ol("sbc\tr27,r31");
         }
      else {
      	ol("sub\tr30,r26");
         ol("sbc\tr31,r27");
         }
      }
}


// Multiply the primary and secondary registers.
// For INTs, result in primary, overflow in secondary.

void gmult(int type) {
	gpop(type);
	gcall("mul", type);
}


void umult(int type) {
	gpop(type);
	gcall("umul", type);
}

// divide the secondary register by the primary
// (quotient in primary, remainder in secondary)

void gdiv(int type) {
	gpop(type);
	gcall("div", type);
}


void udiv(int type) {
	gpop(type);
	gcall("udiv", type);
}

// compute the remainder (mod) of the secondary register
// divided by the primary register
// (remainder in primary, quotient in secondary)

void gmod(int type) {
	gdiv(type);
   if (type == CINT)
   	x2z();
   else
   	x2zL();
}


void umod(int type) {
	udiv(type);
   if (type == CINT)
   	x2z();
   else
   	x2zL();
}


void x2zL(void) {
	ol("mov\tr31,r25");
   ol("mov\tr30,r24");
   ol("mov\tr27,r23");
   ol("mov\tr26,r22");
}


// inclusive 'or' the primary and secondary registers

void gor(int type) {
	gpop(type);
   if (type == CLONG)
		gcall("or", type);
   else {
   	ol("or\tr30,r26");
      ol("or\tr31,r27");
      InX = 0;
      }
}


// exclusive 'or' the primary and secondary registers

void gxor(int type) {
	gpop(type);
   if (type == CLONG)
		gcall("xor", type);
	else {
   	ol("eor\tr30,r26");
      ol("eor\tr31,r27");
      InX = 0;
      }
}


// 'and' the primary and secondary registers

void gand(int type) {
	gpop(type);
   if (type == CLONG)
		gcall("and", type);
   else {
   	ol("and\tr30,r26");
      ol("and\tr31,r27");
      InX = 0;
      }
}


// arithmetic shift right the secondary register the number of
// times in the primary register
// (results in primary register)

void gasr(int type) {
	if (type == CLONG) {
   	ol("mov\tr25,r31");
      ol("mov\tr24,r30");
		ol("rcall\t_pop_l_p");
      ol("rcall\t_lsr_l");
      }
   else {
		gpop(type);
		gcall("lsr", type);
   	x2z();
   	InX = 0;
      }
}


// arithmetic shift left the secondary register the number of
// times in the primary register
// (results in primary register)

void gasl(int type) {
	if (type == CLONG) {
   	ol("mov\tr25,r31");
      ol("mov\tr24,r30");
		ol("rcall\t_pop_l_p");
      ol("rcall\t_lsl_l");
      }
   else {
		gpop(type);
		gcall("lsl", type);
	   x2z();
	   InX = 0;
      }
}


// two's complement of primary register

void gneg(int type) {
	if (type == CLONG)
		gcall("neg", type);
	else {
		ol("com\tr30");
   	ol("com\tr31");
	   ol("adiw\tr30,1");
	   InX = 0;
      }
}


// logical complement of primary register

void glneg(int type) {
	if (InX) {
   	ol("mov\tr31,r27");
      ol("mov\tr30,r26");
      }
	gcall("bool", type);
   InX = 0;
}


// one's complement of primary register

void gcom(int type) {
	if (type == CLONG)
		gcall("com", type);
   else {
   	if (InX) {
      	ol("com\tr26");
         ol("com\tr27");
         }
      else {
   		ol("com\tr30");
      	ol("com\tr31");
         }
      }
}


// Convert primary value into logical value (0 if 0, 1 otherwise)

void gbool(int type) {
	gcall("bool", type);
}


// Increment the primary register by 1 if not a POINTER, otherwise
// by the pointer size.

void ginc(STATE *stpt) {

//   IncPending = 0;
   if (symtab[stpt->ptr].ident == POINTER) {
   	if (stpt->type == CLONG) {
      	if (InX)
         	ol("adiw\tr26,4");
         else
         	ol("adiw\tr30,4");
         }
      else
		if (stpt->type == CINT || stpt->type == UCINT) {
      	if (InX)
         	ol("adiw\tr26,2");
         else
				ol("adiw\tr30,2");
        	}
		else
      if (stpt->type == CCHAR || stpt->type == UCCHAR) {
      	if (InX)
         	ol("adiw\tr26,1");
         else
				ol("adiw\tr30,1");
         }
      else
      if (stpt->type == CSTRUCT) {
         if (InX)
         	ot("adiw\tr30,");
         else
         	ot("adiw\tr30,");
         onum(symtab[symtab[stpt->ptr].pntrpntr].PerEntry);
         nl();
         }
      else
      if (stpt->type == STRUCTINST) {
      	if (InX)
         	ot("adiw\tr26,");
         else
         	ot("adiw\tr30,");
         onum(symtab[symtab[stpt->ptr].pntrpntr].offset);
         nl();
         }
      }
   else {
   	if (symtab[stpt->ptr].type == CLONG) {
      	ol("adiw\tr26,1");
         ol("brcc\t$+4");
         ol("adiw\tr30,1");
         }
      else {
      	if (InX)
         	ol("adiw\tr26,1");
         else
				ol("adiw\tr30,1");
         }
      }
}


// decrement the primary register by one if char, INTSIZE if int

void gdec(STATE *stpt) {

//	DecPending = 0;
   if (symtab[stpt->ptr].ident == POINTER) {
   	if (stpt->type == CLONG) {
      	if (InX)
         	ol("sbiw\tr30,4");
         else
         	ol("sbiw\tr30,4");
         }
      else
		if (stpt->type == CINT) {
      	if (InX)
         	ol("sbiw\tr26,2");
         else
				ol("sbiw\tr30,2");
         }
		else {
      	if (InX)
         	ol("sbiw\tr26,1");
         else
				ol("sbiw\tr30,1");
         }
      }
   else {
		if (symtab[stpt->ptr].type == CLONG) {
			ol("sbiw\tr26,1");
         ol("sbci\tr30,0");
         ol("sbci\tr31,0");
			}
		else {
      	if (InX)
         	ol("sbiw\tr26,1");
         else
				ol("sbiw\tr30,1");
         }
      }
}


// Following are the conditional operators.
// They compare the secondary register against the primary register
// and will branch if the condition tested for is TRUE.

// equal

void geq(int type) {
	gpop(type);
   if (type == CLONG)
		ol("rcall\t_cmp_l");
   else {
		ol("sub\tr30,r26");
	  	ol("sbc\tr31,r27");
      }
	ol("breq\t$+4");
   InX = 0;
}


// not equal

void gne(int type) {
	gpop(type);
   if (type == CLONG)
		ol("rcall\t_cmp_l");
   else {
   	ol("sub\tr30,r26");
      ol("sbc\tr31,r27");
      }
  	ol("brne\t$+4");
   InX = 0;
}


// less than (signed)

void glt(int type) {
	gpop(type);
   if (type == CLONG)
		ol("rcall\t_cmp_l");
   else {
   	ol("sub\tr26,r30");
      ol("sbc\tr27,r31");
      }
	ol("brlo\t$+4");
   InX = 1;
}


// less than or equal (signed)

void gle(int type) {
	gpop(type);
   if (type == CLONG)
		ol("rcall\t_cmp_l");
   else {
   	ol("sub\tr30,r26");
      ol("sbc\tr31,r27");
      }
   ol("brge\t$+4");
   InX = 0;
}


// greater than (signed)

void ggt(int type) {
	gpop(type);
   if (type == CLONG)
 		ol("rcall\t_cmp_l");
   else {
		ol("sub\tr30,r26");
      ol("sbc\tr31,r27");
      }
	ol("brlo\t$+4");
}


// greater than or equal (signed)

void gge(int type) {
	gpop(type);
	if (type == CLONG)
		ol("rcall\t_cmp_l");
   else {
		ol("sub\tr26,r30");
      ol("sbc\tr27,r31");
      }
   ol("brge\t$+4");
}


//********************************************************

// less than (unsigned)

void gult(int type) {
	gpop(type);
//	gcall("ult", type);
	ol("sub\tr26,r30");
   if (type == UCINT)
   	ol("sbc\tr27,r31");
   ol("brlo\t$+4");
}


// less than or equal (unsigned)

void gule(int type) {
	gpop(type);
//	gcall("ule", type);
	ol("sub\tr30,r26");
   if (type == UCINT)
   	ol("sbc\tr31,r27");
   ol("brge\t$+4");
}


// greater than (unsigned)

void gugt(int type) {
	gpop(type);
//	gcall("ugt", type);
	ol("sub\tr26,r30");
   if (type == UCINT)
   	ol("sbc\tr27,r31");
   ol("brlo\t$+4");
}


// greater than or equal (unsigned)

void guge(int type) {
	gpop(type);
//	gcall("uge", type);
	ol("sub\tr26,r30");
   if (type == UCINT)
   	ol("sbc\tr27,r31");
   ol("brsh\t$+4");
}



//*******************************************************

static char *incp;

char *GetIncs(char *name) {
	static char *p;
	char *q;

	if (incp == NULL) 
	{
		incp = (char *)getenv(name);
		if (incp)
		{
			if (*incp == ';')
      		incp++;
			p = q = incp;
		}
		else
			return NULL;
	}
  	else 
	{
      if (*p == ';')
      	p++;
   	q = p;
   }

  	while (*p && *p != ';')
    	p++;
	strncpy(line, q, p-q);
	line[p-q] = '\0';
	if (p-q)
   	return line;
   else
   	return NULL;
}


// Squirrel away argument count in a register that modstk
// doesn't touch.

void gnargs(int d) 
{
}


// Run the assembler immediately after compiling

static char linkline[150];
static char buf[300];

int assemble(char *s) {
	char *p;

	if (strlen(linkline)) {
   	strcat(linkline, " ");
      strcat(linkline, module);
      }
   else
   	strcpy(linkline, module);
	sprintf(buf, "aa90 -r -L -v%d ", Vtype);
   incp = NULL;
   while (p = GetIncs("INCLUDE")) {
   	strcat(buf, "-I");
      strcat(buf, p);
      strcat(buf, " ");
		}
	strcat(buf, module);
	strcat(buf, " -o ");
	strcat(buf, module);
   printf("%s\n", buf);
	return (system(buf));
}


// Run the linker

int link(void) {
	char *p;

	strcpy(buf, "xlink crti libcavr ");
   strcat(buf, linkline);
   incp = NULL;
   while (p = GetIncs("LIB")) {
   	strcat(buf, " -I");
      strcat(buf, p);
		}
   strcat(buf, " -ca90 -Z(DATA)sdata=60 -Z(CODE)scode=0 -Fintel-standard -o ");
   strcat(buf, linkline);
   strcat(buf, ".hex -xsem -l map");
   printf("%s\n", buf);
	system(buf);

	strcpy(buf, "xlink crti libcavr ");
   strcat(buf, linkline);
   incp = NULL;
   while (p = GetIncs("LIB")) {
   	strcat(buf, " -I");
      strcat(buf, p);
		}
   strcat(buf, " -ca90 -r -Z(DATA)sdata=60 -Z(CODE)scode=0 -o debug");
   printf("%s\n", buf);
	return (system(buf));
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -