Thursday, 10 November 2011

design of two pass assemblers

A two pass assembler does two passes over the source file ( the second pass can be over a file generated in the first pass ). In the first pass all it does is looks for label definitions and introduces them in the symbol table. In the second pass, after the symbol table is complete, it does the actual assembly by translating the operations and so on.
The classical two-pass assembly process is adapted for implementation in a functional programming language similar to Backus' FP language. We show that the parallelism inherent in FP languages allows radical changes in the design of such well-known algorithms as the two-pass assembler.
-------------------
//Pass 1 of 2 pass assembler
#include<stdio.h>
#include<conio.h>
#include<string.h>
#include<stdlib.h>
void main()
{
char opcode[10],operand[10],label[10],code[10];
int locctr,start,length;
FILE *fp1,*fp2,*fp3,*fp4;
clrscr();
fp1=fopen(“INPUT.DAT”,”r”);
fp2=fopen(“SYMTB1.DAT”,”w”);
fp3=fopen(“OUT.DAT”,”w”);
fp4=fopen(“OPTAB.DAT”,”r”);
fscanf(fp1,”%s%s%s”,label,opcode,operand);
if(strcmp(opcode,”START”)==0)
{
start=atoi(operand);
locctr=start;
fprintf(fp3,”\t%s\t%s\t%s\n”,label,opcode,operand);
fscanf(fp1,”%s%s%s”,label,opcode,operand);
}
else
locctr=0;
while(strcmp(opcode,”END”)!=0)
{
fprintf(fp3,”%d\t”,locctr);
if(strcmp(label,”**”)!=0)
fprintf(fp2,”%s\t%d\n”,label,locctr);
while(strcmp(code,”END”)!=0)
{
if(strcmp(opcode,code)==0)
{
locctr+=3;
break;
}
fscanf(fp4,”%s”,code);
}
if(strcmp(opcode,”WORD”)==0)
locctr+=3;
else if(strcmp(opcode,”RESW”)==0)
locctr+=(3*(atoi(operand)));
else if(strcmp(opcode,”RESB”)==0)
locctr+=(atoi(operand));
else if(strcmp(opcode,”BYTE”)==0)
++locctr;
fprintf(fp3,”%s\t%s\t%s\n”,label,opcode,operand);
fscanf(fp1,”%s%s%s”,label,opcode,operand);
}
fprintf(fp3,”%d\t%s\t%s\t%s\n”,locctr,label,opcode,operand);
length=locctr-start;
printf(“The length of the program is %d”,length);
fclose(fp1);
fclose(fp2);
fclose(fp3);
fclose(fp4);
getch();
}

a single pass assemblers

Single Pass Assembler Program
Question - Implement a single pass assembler.
Program
#include "stdio.h"
#include "stdlib.h"
#include "string.h"
int count[20];
void main()
{
FILE *f1,*f2,*f3,*f4;
int linenumber,locctr,f;
char lbl[10],mne[10],opd[10],ch,mneu1[10],sval[10];
char sadr[10],slbl[10],op1[10],label[10];
void wordcount();
printf("Word count for Input Program:");
wordcount();
printf("\n Output \n");
printf("\n Source Code \t Object code \n\n");
f1=fopen("INPUT.C","r");
f2=fopen("SYMTAB.C","w+");
f4=fopen("INTER.C","w");
fscanf(f1,"%s %s %x\n",lbl,mne,&locctr);
linenumber=2;
while(!feof(f1))
{
if(count[linenumber]==1)
{
fscanf(f1,"%s\n",mne);
fprintf(f4,"%x\t%s",locctr,mne);
}
if(count[linenumber]==2)
{
fscanf(f1,"%s%s\n",mne,opd);
fscanf(f4,"%X \t %s \t %s \n",locctr,mne,opd);
printf("%s\t%s\t",mne,opd);
f3=fopen("OPCODE.C","r");
while(!feof(f3))
{
fscanf(f3,"%s %s \n",mneu1,op1);
if(strcmp(mne,mneu1)==0)
printf("%s\t",op1);
}
fclose(f3);
f=0;
rewind(f2);
while(!feof(f2))
{
fscanf(f2,"%s %s %s \n",sadr,slbl,sval);
if(strcmp(opd,slbl)==0)
{
printf("%s\n\n",sadr);
f=1;
}
}
if(f==0)
printf("0000\n");
}
if(count[linenumber]==3)
{
fscanf(f1,"%s %s %s \n",lbl,mne,opd);
fprintf(f4,"%X \t %s \t %s \t %s \n",locctr,lbl,mne,opd);
fprintf(f2,"%X \t %s \t %s \n", locctr, lbl,opd);
if((strcmp(mne,"RESW")==0) || (strcmp(mne,"RESB")==0))
printf("%s \t %s \t 00 \t 000 %s \n\n",lbl,mne,opd);
else
printf("%s \t %s \t 00 \t 000 %s \n\n",lbl,mne,opd);
}
linenumber+=1;
if(strcmp(mne,"WORD")==0)
locctr+=3;
else if(strcmp(mne,"BYTE")==0)
locctr+=strlen(opd);
else if(strcmp(mne,"RESW)==0)
locctr+=3 * (atoi(opd));
else if(strcmp(mne,"RESB")==0)
locctr+=atoi(opd);
else
locctr+=3;
}
fclose(f1);
fclose(f2);
fclose(f4);
getch();
}
void wordcount()
{
FILE *f3;
char c;
int word=0,i=1;
printf("\n Word Count");
f3=fopen("INPUT.C","r");
c=fgetc(f3);
while(c!=EOF)
{
if(c==' ')
word+=1;
if(c=='\n')
{
word+=1;
count[i]=word;
printf("\n No.of words in %d:%d",r,word);
i+=1;
word=0;
}
c=fgetc(f3);
}
fclose(f3);
}
INPUT.c
WC START 1000
FIRST WORD 5
SECOND WORD 6
THIRD RESW 1
LDA FIRST
ADD SECOND
STA THIRD
END

elements of assembly programming

Elements of Assembly Language
Assembly language is basically like any other language, which means that it has its words, rules and syntax. The basic elements of assembly language are:
Labels;
Orders;
Directives; and
Comments.
mathematical and logical operations:
NAME OPERATION EXAMPLE RESULT
+ Addition 10+5 15
- Subtraction 25-17 8
* Multiplication 7*4 28
/ Division (with no remainder) 7/4 1
MOD Remainder of division 7 MOD 4 3
SHR Shift register bits to the right 1000B SHR 2 0010B
SHL Shift register bits to the left 1010B SHL 2 101000B
NOT Negation (first complement of number) NOT 1 1111111111111110B
AND Logical AND 1101B AND 0101B 0101B
OR Logical OR 1101B OR 0101B 1101B
XOR Exclusive OR 1101B XOR 0101B 1000B
LOW 8 low significant bits LOW(0AADDH) 0DDH
HIGH 8 high significant bits HIGH(0AADDH) 0AAH
EQ, = Equal 7 EQ 4 or 7=4 0 (false)
NE,<> Not equal 7 NE 4 or 7<>4 0FFFFH (true)
GT, > Greater than 7 GT 4 or 7>4 0FFFFH (true)
GE, >= Greater or equal 7 GE 4 or 7>=4 0FFFFH (true)
LT, < Less than 7 LT 4 or 7<4 0 (false)

Assembler

What Is Assembler?
Assembler is the step comes in between a sorce code and .exe file.the steps are like this Sorce...
What Are The Types Of Assembler?
Meta,cross,macro
What Is Meant By Assembler?
An assembler is "someone who assembles, or builds something"
What Is Compiler, Interpreter, Assembler?
What are the differences between a compiler, interpreter and assembler?
What Is Assembler In System Software?
Assembler is a program that converts computer instrutions into bits that can be processed .

An assembly language is a low-level programming language for computers, microprocessors, microcontrollers, and other programmable devices. It implements a symbolic representation of the machine codes and other constants needed to program a given CPU architecture. This representation is usually defined by the hardware manufacturer, and is based on mnemonics that symbolize processing steps (instructions), processor registers, memory locations, and other language features. An assembly language is thus specific to a certain physical (or virtual) computer architecture. This is in contrast to most high-level programming languages, which, ideally, are portable.
A utility program called an assembler is used to translate assembly language statements into the target computer's machine code. The assembler performs a more or less isomorphic translation (a one-to-one mapping) from mnemonic statements into machine instructions and data. This is in contrast with high-level languages, in which a single statement generally results in many machine instructions.
Many sophisticated assemblers offer additional mechanisms to facilitate program development, control the assembly process, and aid debugging. In particular, most modern assemblers include a macro facility (described below), and are called macro assemblers.

Typically a modern assembler creates object code by translating assembly instruction mnemonics into opcodes, and by resolving symbolic names for memory locations and other entities.[1] The use of symbolic references is a key feature of assemblers, saving tedious calculations and manual address updates after program modifications. Most assemblers also include macro facilities for performing textual substitution—e.g., to generate common short sequences of instructions as inline, instead of called subroutines.
Assemblers are generally simpler to write than compilers for high-level languages,[citation needed] and have been available since the 1950s. Modern assemblers, especially for RISC architectures, such as SPARC or POWER, as well as x86 and x86-64, optimize Instruction scheduling to exploit the CPU pipeline efficiently.[citation needed]
Number of passes

There are two types of assemblers based on how many passes through the source are needed to produce the executable program.
One-pass assemblers go through the source code once. Any symbol used before it is defined will require "errata" at the end of the object code (or, at least, no earlier than the point where the symbol is defined) telling the linker or the loader to "go back" and overwrite a placeholder which had been left where the as yet undefined symbol was used.
Two-pass assemblers create a table with all symbols and their values in the first pass, then use the table in a second pass to generate code.
In both cases, the assembler must be able to determine the size of each instruction on the first or only pass in order to calculate the addresses of symbols. This means that if the size of an operation referring to an operand defined later depends on the type or distance of the operand, the assembler will make a pessimistic estimate when first encountering the operation, and if necessary pad it with one or more "no-operation" instructions in the second pass or the errata.
The original reason for the use of one-pass assemblers was speed of assembly; however, modern computers perform two-pass assembly without unacceptable delay. The advantage of the two-pass assembler is that the absence of a need for errata makes the linker (or the loader if the assembler directly produces executable code) simpler and faster.[2]
High-level assemblers

More sophisticated high-level assemblers provide language abstractions such as:
Advanced control structures
High-level procedure/function declarations and invocations
High-level abstract data types, including structures/records, unions, classes, and sets
Sophisticated macro processing (although available on ordinary assemblers since late 1950s for IBM 700 series and since 1960's for IBM/360, amongst other machines)

An assembler is a program that takes basic computer instructions and converts them into a pattern of bits that the computer's processor can use to perform its basic operations. Some people call these instructions assembler language and others use the term assembly language.