All Task of Assembly Language 2024

This is a site for the record of all test answers for the course Assembly Language, Spring 2024, taught by Леонов Александр Георгиевич, on the online course platform mirera.ru.

You can see some of the points about the classroom in “Some points about Assembly Language 2024”.

Lecture 01

0 (Example)

MOV AX,0	; Move 0 to register AX, i.e., assign the value

2000

Write a program that puts 2000 in the AX register.

MOV AX, 2000

Data

Write a program that puts data from BX in the AX register.

MOV AX, BX

Sum (Example)

Run the program that puts the sum of data from BX and CX into the AX register.

MOV AX,BX
ADD AX,CX

Subtract

Write a program that places the result of subtracting data CX from BX into register AX.

SUB BX, CX
MOV AX, BX

Calculate

Write a program that places the result of operation into register AX.

MOV AX, 0
MOV BX, FF00
MOV CX, F
MOV DX, F1

AND CX, DX
OR  CX, 80

MOV AX, BX
OR  AX, C0
ADD AX, CX
NEG AX

Swap

Write a program that swaps two numbers in registers BX and CX.

MOV AX, BX
MOV BX, CX
MOV CX, AX

Swap Return

Write a program that swaps two numbers in registers BX and CX (Not use Push/Pop or other registers)!

ADD BX, CX
SUB CX, BX
NEG CX
SUB BX, CX

NOT

Bitwise Unary NOT (~) performs complementation or negation operation; inverts all the bits of the number, i.e. 0→1 and 1→0.

  • Truth table:

    A ~ A
    0 1
    1 0

Write a program that places the result of operation NOT into register AX. (Not use Push/Pop or other registers)!

NEG AX
DEC AX

Remember!

Write a program that stores two numbers in registers BX and CX between operations.

PUSH BX
PUSH CX

MOV DX,0
MOV CX,0
MOV BX,0
MOV AX,0

POP CX
POP BX

XOR

Exclusive or or exclusive disjunction is a logical operation that is true if and only if its arguments differ (one is 1, the other is 0). Exclusive disjunction is often used for bitwise operations. Examples:

  • 1 XOR 1 = 0
  • 1 XOR 0 = 1
  • 0 XOR 1 = 1
  • 0 XOR 0 = 0

Write a program that places the result of operation AX XOR BX into register AX. (Not use Push/Pop or all other registers, you can use only one extra register - CX)!

MOV CX, AX
OR  AX, BX
AND BX, CX
NEG BX
DEC BX
AND AX, BX

Left Shift (Example)

Run the program that multiply by 2 a number in the AX register.

Do Not forget CLC before any RCL!

CLC
RCL AX
END

Right Shift

Write a program that divides by 2 the number in register CX and puts the result in register AX.

Do Not forget CLC before any RCR!

CLC
RCR CX
MOV AX, CX

MultiShift

Write a program that puts the value of AX multiplied by 4 into register BX and the value of AX divided by 4 into register CX.

Use the shift operations RCL and RCR.

Do Not forget CLC before any RCL and RCR!

MOV BX, AX
MOV CX, AX

CLC
RCL BX
CLC
RCL BX

CLC
RCR CX
CLC
RCR CX

Sum

Write a program that puts into register AX the sum of two 8-bit numbers stored in 16-bit register BX.

Example: BX = \(032E_{16}\), result AX = \(03_{16} + 2E_{16}\) = \(31_{16}\).

If BX=0, then AX=0.

Use the shift operations RCL or RCR.

Do Not forget CLC before any RCL and RCR!

MOV AX, BX
AND AX, 00FF
MOV CX, BX

CLC
RCR CX
CLC
RCR CX
CLC
RCR CX
CLC
RCR CX
CLC
RCR CX
CLC
RCR CX
CLC
RCR CX
CLC
RCR CX

ADD AX, CX

END

Lecture 02

Zero Comparison (Example)

Run a program that compares BX and CX and sets AX=1 when BX = CX

CMP BX,CX
JNZ ?1
MOV AX,1
?1:

Comparing two numbers

Write a program that puts 1 in register AX if BX \(\ge\) CX and 0 otherwise.

CMP BX, CX
JC  ?01
MOV AX, 1
JMP ?02
?01:
MOV AX, 0
?02:

Absolute value

Write a program to put the absolute value of the difference between the numbers in BX and CX into register AX.

CMP BX, CX
JNC ?01
SUB CX, BX
MOV AX, CX
JMP ?02
?01:
SUB BX, CX
MOV AX, BX
?02:

Minimum

Write a program that puts the minimum number of numbers from BX and CX into AX.

CMP BX, CX
JC  ?01
MOV AX, CX
JMP ?02
?01:
MOV AX, BX
?02:

Divisible by 3

Write a program that puts 1 in register AX if BX is evenly divisible by 3, and 0 otherwise.

MOV AX, BX
MOV CX, 3
JZ  ?03
?01:
SUB AX, 0
JZ  ?03
CMP AX, CX
JC  ?02
JZ  ?03
SUB AX, CX
JMP ?01

?02:
MOV AX, 0
JMP ?04

?03:
MOV AX, 1

?04:

Divisible by 2

Write a program that puts 1 in register AX if BX is evenly divisible by 2, and 0 otherwise.

(Do not use all other registers, except AX and BX or any Jump command)!

MOV AX, 1
AND BX, 1
SUB AX, BX

Bit number

Bits in a 16-bit register are numbered from 1 (least significant bit) to 16. Write a program that finds the least significant non-zero bit number of register BX and puts the answer into register AX.

If BX=0, then AX=0.

Use the RCR shift operation.

Example: BX=\(0006_{16}\) (0000 0000 0000 01102), AX=2.

MOV CX, 0
MOV AX, BX

OR  AX, AX
JZ  ?01
MOV CX, 1

?02:
RCR BX
JC  ?03
INC CX
JMP ?02

?03:
MOV AX, CX
JMP ?04

?01:
MOV AX, 0

?04:

Number of different numbers

Write a program that puts in register AX the number of different numbers in BX, CX, DX.

Example:

  • DX = 0
  • BX = 1
  • CX = 2
  • Answer AX = 3
MOV AX, 3
CMP BX, CX
JNZ ?01
DEC AX

?01:
CMP BX, DX
JNZ ?02
DEC AX

?02:
CMP CX, DX
JNZ ?03
DEC AX

?03:
CMP AX, 1
JNC ?04
MOV AX, 1

?04:

Number of maximum

Write a program that counts the maximums in the sequence BX, CX, DX and places the result in the AX register. For example, in the sequence of numbers 1,2,3 - the maximum is unique and equals 3 (BX=1, CX=2, DX=3 ⇒ AX=1) In the sequence of numbers 3,1,3 - the maximum is 3 and there are 2 such numbers in the sequence (BX=3, CX=1, DX=3 ⇒ AX=2).

MOV AX, 1
?00:
CMP BX, CX
JC  ?01
JZ  ?02
?03:
CMP BX, DX
JC  ?04
JZ  ?05
JMP ?06
?01:
MOV BX, CX
MOV AX, 1
JMP ?03
?02:
INC AX
JMP ?03
?04:
MOV BX, DX
MOV AX, 1
JMP ?06
?05:
INC AX
JMP ?06
?06:

Sides of a triangle

Can non-negative integers in BX, CX, DX be sides of a triangle?

The result will be AX=1 if YES and AX=0 if NOT.

ADD BX, CX
MOV AX, BX
SUB BX, CX
SUB AX, DX
JZ  ?00
JC  ?00
MOV AX, 1

ADD BX, DX
MOV AX, BX
SUB BX, DX
SUB AX, CX
JZ  ?00
JC  ?00
MOV AX, 1

ADD CX, DX
MOV AX, CX
SUB CX, DX
SUB AX, BX
JZ  ?00
JC  ?00
MOV AX, 1
JMP ?03

?00:
MOV AX, 0

?03:

Right triangle

Can non-negative integers in BX, CX, DX be sides of a right triangle?

The result will be AX=1 if yes, and AX=0 if not.

Note. A triangle with sides {0,0,0} is not a right triangle.

PUSH DX
PUSH CX
MOV AX, BX
MOV CX, BX
DEC AX

?01:
ADD BX, CX
DEC AX
JZ  ?02
JMP ?01

?02:
POP CX
POP DX

PUSH BX
PUSH DX
MOV AX, CX
MOV BX, CX
DEC AX

?03:
ADD CX, BX
DEC AX
JZ ?04
JMP ?03

?04:
POP DX
POP BX

PUSH BX
PUSH CX
MOV AX, DX
MOV BX, DX
DEC AX

?05:
ADD DX, BX
DEC AX
JZ ?06
JMP ?05

?06:
POP CX
POP BX

MOV AX, 0

CMP BX, 0
CMP CX, 0
CMP DX, 0
JZ  ?07

ADD BX, CX
CMP BX, DX
JZ  ?09
SUB BX, CX

ADD BX, DX
CMP BX, CX
JZ  ?09
SUB BX, DX

ADD CX, DX
CMP CX, BX
JZ  ?09
SUB CX, DX
JMP ?07

?09:
MOV AX, 1
?07:

Long shift to the left

Run a program that doubles a 32-bit number from the BX AX registers (lower part of AX).

RCL shift operations are used.

CLC
RCL AX
RCL BX

Long shift to the right

Write a program that divides a 32-bit number from the BX AX registers (lower part of AX) by 4.

RCR shift operations are used.

RCR BX
RCR AX

RCR BX
RCR AX

Adding two long

Write a program that adds a 32-bit long number stored in the CX, DX registers with a long number stored in the AX, BX registers.

ADD BX, DX
JC  ?00
JMP ?01
?00:
INC AX
?01:
ADD AX, CX

Bus for programmers

Bus tickets for programmers have a hexadecimal number. We call a ticket lucky if the sum of the two left hexadecimal digits is equal to the sum of the two right digits, for example ADE9. Example of an unsuccessful ticket: 7+8≠9+3. How many lucky ticket numbers are found from number BX to number CX, including borders?

; Code to achieve the task goal: to determine whether a number is a lucky vote or not
; Method: Read four 4-bit binary numbers in sequence using 0 and 1 operations, and then use RCR to transfer the data to the real data.
; Then, judge whether the final result is 0 by adding and subtracting to determine whether it is a lucky number of votes.

SUB CX, BX          ; Subtract BX from CX, result stored in CX
ADD CX, 2           ; Add 2 to CX, adjusting the loop counter

?00: 
DEC CX              ; Decrement CX by 1
JZ ?03              ; Jump to label ?03 if CX is zero (end of loop condition)

MOV [1], BX         ; Store the value of BX into memory location addressed by 1
AND BX, 0F          ; Perform bitwise AND between BX and 0F, isolating the lowest 4 bits

MOV DX, BX          ; Move the result of AND operation into DX

MOV BX, [1]         ; Restore BX from memory location addressed by 1
AND BX, F0          ; Perform bitwise AND between BX and F0, isolating bits 4-7
CLC                 ; Clear carry flag to prepare for rotate operation
RCR BX              ; Rotate BX right through carry, shifting bits 4-7 to 0-3
RCR BX
RCR BX
RCR BX              ; Repeat rotation to complete the shift of bits 4-7 to 0-3

ADD DX, BX          ; Add the newly shifted bits in BX to DX

MOV BX, [1]         ; Restore BX from memory location addressed by 1
AND BX, F00         ; Perform bitwise AND between BX and F00, isolating bits 8-11
CLC                 ; Clear carry flag to prepare for rotate operation
RCR BX              ; Rotate BX right through carry, shifting bits 8-11 towards lower bit positions
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX              ; Repeat rotation to complete the shift of bits 8-11 to 0-3

SUB DX, BX          ; Subtract the shifted value in BX from DX

MOV BX, [1]         ; Restore BX from memory location addressed by 1
AND BX, F000        ; Perform bitwise AND between BX and F000, isolating bits 12-15
CLC                 ; Clear carry flag to prepare for rotate operation
RCR BX              ; Rotate BX right through carry, shifting bits 12-15 towards lower bit positions
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX
RCR BX              ; Repeat rotation to complete the shift of bits 12-15 to 0-3

SUB DX, BX          ; Subtract the final shifted value in BX from DX

CMP DX, 0           ; Compare DX with 0
JZ ?01              ; Jump to label ?01 if DX is zero (if comparison equals zero)
MOV BX, [1]         ; Restore BX from memory location addressed by 1
INC BX              ; Increment BX
JMP ?00             ; Jump back to start of loop at label ?00

?01: 
INC AX              ; Increment AX
MOV BX, [1]         ; Restore BX from memory location addressed by 1
INC BX              ; Increment BX
JMP ?00             ; Jump back to start of loop at label ?00

?03:                ; Label ?03, marks the end of the loop or a specific condition block

Lecture 03

Contents of an Address

Write a program that puts the contents at address BX into register AX.

MOV AX, [BX]

Contents of 2

Write a program that gets the number plus 200 from the BX register. Place the result in the AX register.

Example: BX=\(100_{16}\) ⇒ AX=\(300_{16}\)

ADD BX, 200
MOV AX, BX

Contents of an Address 3

Write a program that gets the number plus \(200_{16}\) located at address BX. Place the result in the AX register.

ADD [BX], 200
MOV AX, [BX]

Sum of three numbers

Write a program that puts the sum of the three numbers at addresses 0, 1, and 2 into register AX.

ADD AX, [0]
ADD AX, [1]
ADD AX, [2]

Amount by address

Write a program that substitutes into register AX the sum of three numbers located at addresses BX, BX+1, BX+2.

ADD AX, [BX]
INC BX
ADD AX, [BX]
INC BX
ADD AX, [BX]

Array Sum

Write a program that puts into register AX the sum of an array of length CX, starting at address BX.

The sum of an empty array is 0.

?00:
CMP CX, 0
JZ  ?01

ADD AX, [BX]
DEC CX
INC BX
JMP ?00

?01:

Equal array

Write a program that puts 1 in register AX if all elements of an array of length CX are equal. The array starts at address BX. The answer is 1 if the array has length 0.

MOV AX ,  1
MOV DX ,  [BX]

CMP CX ,  0
JZ  ?02
CMP CX ,  1
JZ  ?02

DEC CX
?00: 
CMP CX ,  0
JZ  ?02

INC BX
DEC CX

CMP DX ,  [BX]
JNZ ?01
JMP ?00

?01: 
MOV AX ,  0

?02: 

Address of the first minimum number

Write a program that places the address of the first minimum number in an array of length CX into register AX, starting at address BX.

In the case of an empty sequence, the answer is 0.

MOV AX, 0
CMP CX, 0
JZ  ?02

MOV AX ,  BX
MOV DX ,  [BX]

?00: 
CMP DX ,  [BX]
JC  ?01
JZ  ?01
MOV DX ,  [BX]
MOV AX ,  BX

?01: 
INC BX
DEC CX
JZ ?02
JMP ?00

?02: 

The number of all connected increasing subsequences

Write a program that count all connected increasing subsequences. Places the result of an array of length CX, starting at address BX nto register AX.

In the case of an empty sequence, the answer is 0.

Example: 1 2 3 2 3 1 ⇒ AX=3.

MOV AX ,  0
CMP CX ,  0
JZ  ?02

MOV AX , 1
MOV DX ,  [BX]
INC BX

?00: 
DEC CX
CMP CX ,  0
JZ  ?02
CMP DX ,  [BX]
JZ  ?01
JNC  ?01
MOV DX ,  [BX]
INC BX
JMP ?00

?01: 
INC AX
MOV DX ,  [BX]
INC BX
JMP ?00

?02:

Address of the second maximum

The CX register contains a value - the number of elements of the sequence located starting from the address BX.

In the case of an empty sequence, the answer is 0

If there is no second maximum, the answer is 0.

Example: 1 2 3 2 3 1 ⇒ AX=5.

MOV AX ,  0
MOV [01F8] , 0			; A null address is needed for data transit in this task, and a random address is chosen here, but this is not a good method.
MOV DX ,  [BX]
ADD CX ,  2

?00: 
DEC CX
CMP CX ,  0
JZ  ?10

CMP DX ,  [BX]
JZ  ?01
JC  ?03
INC BX
JMP ?00

?01: 
INC [01F8]
CMP [01F8] ,  2
JZ  ?02
INC BX
JMP ?00


?02: 
MOV AX ,  BX
JMP ?00

?03: 
MOV DX ,  [BX]
MOV [01F8] ,  1
INC BX
JMP ?00

?10: 

Number of local maxima of the sequence

Write a program, after the execution of which, the register AX will contain the number of local maxima of the sequence.

The CX register contains a value - the number of elements of the sequence located starting from the address BX.

In the case of an empty sequence, the answer is 0.

An element of a non-empty sequence is called a local maximum if it has no neighbor greater than itself. For example, a sequence of one element has one local maximum. The sequence 4, 4, 2, 3, 0 has three local maxima: the first, second, and penultimate elements.

; In order to prevent the data outside the specified array will affect the data at both ends, the first judgement CX is not 0, 
; then it is a separate judgement of whether the data at both ends are satisfied, and then it is a judgement of whether the data in the middle is satisfied, 
; the trap is that if the target data of the right side of the data is greater than it, jump out of the body of the program, at this time, BX (which can be taken as a positional pointer) is still parked in the previous one, and we would like to carry out the judgemental force of the next data, so we should update the BX in time.

MOV AX , 0
CMP CX , 0
JZ  ?00

MOV DX ,  [BX]
INC BX
CMP DX ,  [BX]
JC  ?01
INC AX

?01: 
DEC BX
ADD BX ,  CX
DEC BX

MOV DX ,  [BX]
DEC BX
CMP DX ,  [BX]
JC  ?02
INC AX

?02: 

SUB CX ,  2
JZ ?00

?04: 
MOV DX ,  [BX]
INC BX
CMP DX ,  [BX]
JC  ?03
SUB BX , 2
CMP DX ,  [BX]
JC  ?05
INC AX
JMP ?05

?03: 
SUB BX,2
JMP ?05

?05:
SUB CX ,  1
JNZ ?04

?00: 

The lengths of the sides form a parallelogram

The array contains the lengths of the sides of the parallelogram as it is traversed clockwise.

Write a program that puts 1 in register AX if the elements of the array (lengths of sides) of size CX, starting at address BX, form a parallelogram, and zero otherwise.

In case of error data (CX≠4) the answer is 0.

MOV AX , 0
CMP CX ,  4
JNZ  ?00

MOV DX ,  [BX]
ADD BX ,  2
CMP [BX] ,  DX
JNZ ?00

ADD BX , 1
MOV DX ,  [BX]
SUB BX , 2
CMP [BX] ,  DX
JNZ ?00

MOV AX , 1

?00: 

Lecture 04

The subsequence

In memory at address 0, there is a value - the number of elements of the sequence located starting from address 1.

Write a program that leaves the AX register the number of occurrences of the subsequence “1, 2, 3, 1”.

In the case of an empty sequence, the answer is 0

Example: 7 1 2 3 1 2 3 1 ⇒ AX=2.

It is not emphasised here that “1, 2, 3, 1, 2, 3” should be judged as 2 subsequences.

MOV AX ,  0
MOV BX ,  0
CMP [BX] ,  4
JC  ?00

?01: 
MOV CX ,  [0]
INC CX
CMP BX ,  CX
JZ  ?00
INC BX

CMP [BX] , 1
JZ  ?02
JMP ?01

?02: 
INC BX
CMP [BX] , 2
JZ  ?03
JMP ?01

?03: 
INC BX
CMP [BX] , 3
JZ  ?04
JMP ?01

?04: 
INC BX
CMP [BX] ,  1
JZ  ?05
JMP ?01

?05: 
INC AX
DEC BX ;The last number is 1 and the counter BX has to go backwards by one, in order to check if this 1 might be the beginning of a subsequence.
JMP ?01

?00: 

Even-odd

In memory at address 0, there is a value - the number of elements of an array of natural numbers (and zero also), located starting from address 1.

Let’s call a “strange ascent” the case when there are either even or odd numbers nearby, or the number on the left is odd and the number on the right is even.

Write a program that sorts an array in “strange ascending” order.

Example: 4 3 2 1 2 2 1 ⇒ 3 1 1 4 2 2 2

Remark: Do not change order inside the equivalent class. Wrong answer: 3 1 1 2 4 2 2.

The key to this task is to filter out the odd and even numbers without changing the order in which they are each arranged, and then, arrange the odd numbers first and then the even numbers. Note that the RCR approach is used when determining whether the data in memory is odd or even, but you can’t operate directly on that data because it will affect the data in the memory before and after.

CMP [0] ,  0
JZ  ?00
MOV BX ,  0


?02: 
CMP BX ,  [0]
JZ  ?03
INC BX

CLC
MOV DX , [BX]
RCR DX
JC  ?01
JMP ?02

?01: 
PUSH [BX]
JMP ?02

?03: 
MOV BX ,  0

?04: 
CMP BX ,  [0]
JZ  ?06
INC BX

CLC
MOV DX , [BX]
RCR DX
JNC ?05
JMP ?04

?05: 
PUSH [BX]
JMP ?04

?06: 
MOV BX ,  [0]

?07: 
CMP BX ,  0
JZ  ?00
POP [BX]
DEC BX
JMP ?07
  
?00: 

Adding two long numbers

Write a program that implements the operation of adding two very long numbers.

Integers in the range 0 to \(2^{1024}-1\) are represented as 𝑁 ≤ 64 consecutive words of memory each.

Register AX is the address of the first least significant word of the first number, BX=𝑁 is the length of the number.

The numbers are in order, so the address of the first digit of the second number is AX+BX. The result must be in the first number.

This task pays special attention to the progression, whether there are two numbers produced by adding them together or by the progression of the previous sum.

MOV DX ,  0
MOV CX ,  BX

?00: 
CMP AX ,  CX
JZ  ?03
CLC
ADD [AX] , [BX]
JC  ?01
CLC
ADD [AX] ,  DX
JC  ?02
MOV DX ,  0

INC AX
INC BX
JMP ?00

?01: 
ADD [AX] ,  DX
INC AX
MOV DX , 1
INC BX
JMP ?00

?02: 
INC AX
MOV DX ,  1
INC BX
JMP ?00

?03: 

Multiplying a number by 2

Write a program that implements the operation of multiplying the first of very long number number by 2.

Integers in the range 0 to \(2^{1024}-1\) are represented as 𝑁 ≤ 64 consecutive words of memory each.

Register AX is the address of the first least significant word of the first number, BX=𝑁 is the length of the number.

The result must be in the first number.

MOV AX ,  0
MOV DX ,  0

?00: 
CMP AX ,  BX
JZ  ?02
CLC
ADD [AX] , [AX]
JC  ?01
ADD [AX] ,  DX
MOV DX ,  0
INC AX
JMP ?00

?01: 
ADD [AX] ,  DX
INC AX
MOV DX ,  1
JMP ?00

?02: 

Dividing a number by 2

Write a program that implements the operation of dividing the first of very long number number by 2.

Integers in the range 0 to \(2^{1024}-1\) are represented as 𝑁 ≤ 64 consecutive words of memory each.

Register AX is the address of the first least significant word of the first number, BX=𝑁 is the length of the number.

The result must be in the first number.

The pitfall of this task is that it is possible to use successive RCRs to process the data in order from high to low, but it will destroy the contents of the C flag when determining whether the loop needs to end, so it needs to be specially documented.

CLC

?00: 
RCR [BX]
JC  ?01
CMP BX ,  0
JZ  ?10
DEC BX
JMP ?00

?01: 
CMP BX ,  0
JZ  ?10
DEC BX
CMP BX ,  FFFF
JMP ?00

?10: 

Lecture 05

Padovan problem by C

A sequence of integers is read from input using the input.txt file.

Answer (0-no, 1-yes) output to output.txt file

In the case of an empty sequence, an empty file must be created.

\[a_0=1, a_1=1, a_2=1, an=a_{n-2}+a_{n-3}\]
#include <stdio.h>

int recurrent(FILE *fin, int a0);

int main(void)
{
    FILE *fin, *fout;
    fin = fopen("input.txt", "r");
    fout = fopen("output.txt", "w");
    int a0;
    
    if ((fin != NULL) && (fscanf(fin, "%d", &a0) != EOF))
    {
        fprintf(fout, "%d", recurrent(fin, a0)); 
    }
    
    fclose(fin);
    fclose(fout);
    return 0;
}

int recurrent(FILE *fin, int a0)
{   
 
}

Copy the sequence

A sequence of integers in the input stream.

For reading, the inputInt function is used - returning the read number in the EAX register and the Z=1 flag, in case of reading the end of the file.

We need to copy the sequence from the input stream to the output stream.

Functions are used for output.

printiInt - prints the integer contained in the EAX register,

printiEndl - go to another line,

You can also use the printiHex function - prints the hexadecimal representation of the CL register.

All output functions store the values of all registers except the flag registers.

In the case of an empty sequence, the program exit code is -1.

extern printEndl, printInt, inputInt, printHex  ; Declare external functions that are used for I/O
%include 'conio.h'                             ; Include console input/output header

section .text                                  ; Begin the text (code) section of the assembly file
global _start                                  ; Declare the _start label as global so it's visible to the linker

_start:                                        ; The entry point of the program

call inputInt                                  ; Call inputInt to read an integer from standard input
mov rdi,-1                                     ; Preset rdi with -1, which is potentially used for error signaling
jz .exit                                       ; If zero flag is set (inputInt read EOF), jump to .exit
call printInt                                  ; Call printInt to print the integer in EAX
call printEndl                                 ; Call printEndl to print a newline

.repit:                                        ; Label for the beginning of the loop
call inputInt                                  ; Call inputInt to read the next integer from standard input
jz .exit0                                      ; If zero flag is set (inputInt read EOF), jump to .exit0
call printInt                                  ; Call printInt to print the integer in EAX
call printEndl                                 ; Call printEndl to print a newline
jmp .repit                                     ; Jump back to the start of the loop

.exit0:                                        ; Label for exiting after printing all integers
xor rdi, rdi                                   ; Clear rdi register (sets the value to 0) to signal successful end
.exit:                                         
mov rax, 60                                    ; Load the sys_exit system call number into rax
syscall                                        ; Make the system call to exit the program

Maximum of the sequence

A sequence of integers in the input stream.

For reading, the inputInt function is used - returning the read number in the EAX register and the Z=1 flag, in case of reading the end of the file.

We need to find the maximum of the sequence and print the answer to the output stream.

Functions are used for output.

printiInt - prints the integer contained in the EAX register,

printiEndl - go to another line,

You can also use the printiHex function - prints the hexadecimal representation of the CL register.

All output functions store the values of all registers except the flag registers.

In the case of an empty sequence, the program exit code is -1.

extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .text
global _start

_start:

    call inputInt         
    jz .emptySequence     

    mov ebx, eax          

.findMaxLoop:
    call inputInt         
    jz .printMax          

    cmp eax, ebx          
    jle .findMaxLoop      
    mov ebx, eax          
    jmp .findMaxLoop      

.printMax:
    mov eax, ebx          
    call printInt         
    call printEndl        
    jmp .exit             

.emptySequence:
    mov rax, 60
    mov edi, 255
    syscall

.exit:
    mov eax, 60           
    xor edi, edi          
    syscall               

Padovan problem

A sequence of integers in the input stream.

Answer (0-no, 1-yes) to the output stream, is it a Padovan sequence?

In the case of an empty sequence, the program exit code is -1.

\[a_0=1, a_1=1, a_2=1, an=a_{n-2}+a_{n-3}\]

One note of caution here, rax must be assigned the value 60 on return.

extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .text
global _start

_start:

    call inputInt
    jz .errexit
    cmp eax, 1
    jnz .notpad
    call inputInt
    jz .ispad
    cmp eax, 1
    jnz .notpad
    call inputInt
    jz .ispad
    cmp eax, 1
    jnz .notpad
    
    
    mov ebx, 1
    mov ecx, 1
    mov edx, 1

.lp:
    call inputInt
    jz .ispad
    
    add ebx, ecx
    mov r8d, ebx
    mov ebx, ecx
    mov ecx, edx
    mov edx, r8d
    cmp eax, edx
    jnz .notpad
    jmp .lp

.ispad:
    mov eax, 1
    xor rdi, rdi
    call printInt
    jmp .exit
    
.notpad:
    mov eax, 0
    xor rdi, rdi
    call printInt
    jmp .exit
    
.errexit:
    mov rdi, -1
    mov rax, 60
    syscall

.exit:
    mov rax, 60
    syscall

Missing number

The sequence contains integers from 1 to N in arbitrary order, but one of the numbers is missing (the rest occur exactly once). N is not known in advance. Find the missing number.

A sequence of integers in the input stream.

Answer to the output stream.

IIn the case of an empty sequence, the program exit code is -1.

Since we don’t know how many numbers there are and the order of the series, then we can only determine the number of numbers, then find the series sum if there are no missing numbers, and then subtract the actual series sum to get what the missing numbers are.

extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .text
global _start

_start:

    call inputInt
    jz .errexit
    
    mov ebx, 1
    mov ecx, eax
    mov edx, 1

.lp:
    call inputInt
    jz .lpend
    add ebx, 1
    add edx, ebx
    add ecx, eax
    jmp .lp

.lpend:
    add ebx, 1
    add edx, ebx
    sub edx, ecx
    mov eax, edx
    call printInt
    jmp .exit
    
.errexit:
    mov rdi, -1
    mov rax, 60
    syscall

.exit:
    xor rdi, rdi
    mov rax, 60
    syscall

Number - loner

The sequence contains integers from 1 to N. All numbers except one are written twice in random order, one of the numbers is written once. N is not known in advance. Find a number that occurs once.

A sequence of integers in the input stream.

Answer to the output stream.

In the case of an empty sequence, the program exit code is -1.

This task involves multiplication and division, but of course you can add and subtract instead, but it’s too tedious.

extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .text
global _start

_start:

    call inputInt
    jz .errexit
    
    mov ebx, 1
    mov ecx, eax
    
.lp:
    call inputInt
    jz .endlp
    add ebx, 1
    add ecx, eax
    jmp .lp

.endlp:
    mov eax, ebx
    mov eax, ecx
    add ebx, 1
    mov eax, ebx
    mov ebx, 2
    div ebx
    mov ebx, eax
    add eax, 1
    mul ebx
    sub eax, ecx
    call printInt
    jmp .exit
    
.errexit:
    mov rdi, -1
    mov rax, 60
    syscall

.exit:
    xor rdi, rdi 
    mov rax, 60
    syscall

Find the number

The sequence contains integers, more than half of which are equal to the same number X.

It is necessary to find this number X. It is guaranteed that such a number exists.

A sequence of integers in the input stream.

Answer to the output stream.

In the case of an empty sequence, the program exit code is -1.

This task requires the use of the “Moore’s Vote Algorithm”, the catch being that a number is read before it is judged to be empty, so the initial state of the counter is 1 and not 0.

extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .text
global _start

_start:

    call inputInt
    jz .errexit
    
    mov ecx, eax
    mov edx, 1
    
.lp:
    call inputInt
    jz .exit
    cmp edx, 0
    jz .new
    cmp ecx, eax
    jz .count
    sub edx, 1
    jmp .lp
    
.new:
    mov ecx, eax
    mov edx, 1
    jmp .lp
    
.count:
    add edx, 1
    jmp .lp

.errexit:
    mov rdi, -1
    mov rax, 60
    syscall
    
.exit:
    xor rdi, rdi
    mov eax, ecx
    call printInt
    mov rax, 60
    syscall

Second highest (silver)

The second largest element is the one that becomes the largest element in the sequence after all elements with the highest value have been removed from it.

A sequence of integers in the input stream.

Answer to the output stream.

In the case of an empty sequence, the program exit code is -1.

Negative numbers will appear in the program verification of the task, so the compare operation instruction should only be used with signed comparisons.

extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .text
global _start

_start:
    
    call inputInt
    jz .errexit
    mov ebx, eax
    call inputInt
    jz .emptyexit
    mov ecx, eax
    cmp ecx, ebx
    jl .lp
    mov eax, ebx
    mov ebx, ecx
    mov ecx, eax
    
.lp:
    call inputInt
    jz .ifequ
    cmp eax, ebx
    jz .lp
    jge .s1
    cmp eax, ecx
    jz .lp
    jge .s2
    jmp .lp
    
.s1:
    mov ecx, ebx
    mov ebx, eax
    jmp .lp
    
.s2:
    mov ecx, eax
    jmp .lp
    
.ifequ:
    cmp ebx, ecx
    jz .emptyexit
    jmp .exit
    
.errexit:
    mov rdi, -1
    mov rax, 60
    syscall

.emptyexit:
    mov rdi, 0
    mov rax, 60
    syscall

.exit:
    mov rdi, 0
    mov eax, ecx
    call printInt
    mov rax, 60
    syscall

The sum of pairwise products

Find the sum of all pairwise products of a sequence

A sequence of integers in the input stream.

Answer to the output stream.

In the case of an empty sequence, the program exit code is -1.

Assuming that we have only one chance to read the array and we don’t want to request dynamic memory, the problem must be solved in \(O(n)\), and that requires a formula:

\[SUM = \frac{1}{2}((\sum_{i=1}^na_i)^2-\sum_{i=1}^na_i^2)\]
extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .text
global _start

_start:

    xor ebx, ebx
    xor ecx, ecx
    
    call inputInt
    jz .errexit
    
    add ebx, eax
    mul eax
    add ecx, eax
    
    call inputInt
    jz .errexit
    
    add ebx, eax
    mul eax
    add ecx, eax
    
.lp:
    call inputInt
    jz .endlp
    add ebx, eax
    mul eax
    add ecx, eax
    jmp .lp
    
.errexit:
    mov rdi, -1
    mov rax, 60
    syscall

.endlp:
    mov eax, ebx
    mul eax
    sub eax, ecx
    clc
    rcr eax, 1
    call printInt
    
.exit:
    mov rdi, 0
    mov rax, 60
    syscall

Copy array

An array of integers is located in the file input stream. It is required to create an array of N<100 elements and read the array.

You need to copy all array to the output stream.

In the case of an empty sequence, the program exit code is -1.

; External function declarations
extern printEndl, printInt, inputInt, printHex
%include 'conio.h'  ; Include the conio.h library for console input-output support

section .bss
A:resd 100  ; Allocate space for an array, defining array A to hold 100 integers

section .text
global _start  ; Declare _start as globally visible so that the linker can find the entry point of the program

_start:  ; Start of the program

mov ecx,0   ; Initialize counter ecx to 0, for array indexing
mov ebx,A   ; Assign the address of array A to ebx, for subsequent read/write operations

.readA:  ; Label for reading input
call inputInt  ; Call inputInt to read an integer from standard input into eax
jz .eofA  ; If the input is 0, jump to .eofA to handle end-of-file condition
mov [A+ecx*4],eax;  ; Store the read integer at the corresponding position in array A
inc ecx  ; Increase the value of ecx, moving to the next position in the array
jmp .readA  ; Jump back to .readA to continue reading the next integer

.eofA:  ; Handle end-of-input condition
mov rdi,-1  ; Store -1 in rdi, set as error return code
test ecx,ecx  ; Test if ecx is 0 (i.e., if the array is empty)
jz .exit  ; If the array is empty, jump directly to .exit to exit the program

mov ebx,A  ; Reset ebx to the starting address of array A
.writeA:  ; Start writing label
mov eax,[ebx]  ; Read the current element from array A into eax
call printInt  ; Call printInt to print the value of eax
call printEndl  ; Print a newline
add ebx,4  ; Move ebx to the next element in the array
loop .writeA  ; Use ecx as a counter to loop through .writeA using the loop instruction

xor rdi, rdi ; Clear rdi, set as success return code

.exit:  ; Exit label
mov rax, 60  ; Set rax to 60, corresponding to the sys_exit system call number
syscall  ; Perform a system call to exit the program

Sort array

An array of integers is located in the file input stream. It is required to create an array of N<100 elements and read the array.

You need to sort an array of integers in ascending order to the output stream.

In the case of an empty sequence, the program exit code is -1.

; External function declarations
extern printEndl, printInt, inputInt, printHex
%include 'conio.h'  ; Includes the conio.h library for console input-output support

section .bss
A:resd 100  ; Reserves space for an array of 100 integers

section .text
global _start  ; Declares _start as globally visible, marking the entry point of the program

_start:  ; Program start

mov ecx, 0  ; Clears the ecx register, to be used as the array index
mov ebx, A  ; Loads the address of array A into ebx for array operations
.readA:  ; Start of the loop to read the array
call inputInt  ; Calls inputInt function to read an integer from standard input
jz .eofA  ; If input is zero, jump to .eofA to handle end of input
mov [A+ecx*4], eax;  ; Stores the input integer at the current index position in the array
inc ecx  ; Increments index, preparing to read the next value
jmp .readA  ; Jumps back to the start of the read loop

.eofA:
mov rdi, -1  ; Sets return error code to -1
test ecx, ecx  ; Tests if ecx is zero, i.e., if the array is empty
jz .exit  ; If the array is empty, jumps to exit

mov ebx, A  ; Resets ebx to point to the start of the array
call _sort  ; Calls the _sort function to sort the array

mov ebx, A  ; Again sets ebx to point to the start of the array
.writeA:  ; Starts the loop to write the array
mov eax, [ebx]  ; Reads the current element from the array
call printInt  ; Calls printInt to print the current integer
call printEndl  ; Calls printEndl to print a newline
add ebx, 4  ; Moves to the next element in the array
loop .writeA  ; Continues to output using loop instruction until ecx decrements to zero

xor rdi, rdi ; Clears the rdi register, sets the success return code

.exit:
mov rax, 60  ; Sets rax to 60, corresponding to the sys_exit system call
syscall  ; Performs a system call to exit the program

_sort:
pushq  ; Saves register state
dec ecx  ; Decrement array length by one, preparing for sorting
.?loop1:  ; Label for the first loop
push rcx
push rbx

.?loop2:  ; Label for the second loop

mov eax, [ebx]  ; Takes the current element from the array
cmp eax, [ebx+4]  ; Compares it with the next element
jle .?1  ; If the current element is less than or equal to the next, skip swapping
xchg eax, [ebx+4]  ; Swaps the two elements
mov [ebx], eax

.?1:
add bx, 4  ; Moves to the next element
loop .?loop2  ; Continues the inner loop

pop rbx
pop rcx
loop .?loop1  ; Continues the outer loop
popq  ; Restores register state
ret  ; Returns to the calling point

Even strange (Odd)

An array of integers is located in the file input stream. It is required to create an array of N<100 elements and read the array.

You need to output:

- the maximum even element, if the number of even elements is not less than the number of odd ones;

- the maximum odd element, if the number of odd elements is greater than even ones.

For example, for an array of six elements equal to 4, 6, 12, 17, 3, 8, respectively, the answer will be 12 - the largest even number, since there are more even numbers in this array.

Answer to the output stream.

In the case of an empty sequence, the program exit code is -1.

The -2147483648 set here is the smallest negative number that can be stored in a 32-bit register, i.e. it ranges from -2147483648 to 2147483647.

The test instruction is essentially a logical and arithmetic instruction, but it does not save the result of the operation; if the result of the operation is 0, then ZF = 1, for example:

test al, 1
jz even  ; If the lowest bit of al is 0, then jump to the even tag and al is an even number

test ebx, ebx
jz is_zero  ; If ebx is 0, jump to is_zero tag
extern printEndl, printInt, inputInt, printHex
%include 'conio.h'

section .bss
A:resd 100  ; space for an array

section .text
global _start

_start:

    mov ecx, 0      
    mov ebx, A      
    
    mov edi, -2147483648  
    mov esi, -2147483648  
    mov edx, 0            
    mov ebp, 0            

.read_loop:
    call inputInt        
    test eax, eax        
    jz .finalize          
    mov [ebx+ecx*4], eax 
    inc ecx              

    
    test eax, 1          
    jnz .odd_number 
    
.even_number:
    inc edx              
    cmp eax, esi         
    jle .skip_even        
    mov esi, eax         
    jmp .skip_odd
    
.odd_number:
    inc ebp              
    cmp eax, edi         
    jle .skip_odd        
    mov edi, eax  
    
.skip_odd:
.skip_even:
    jmp .read_loop      

.finalize:    
    test ecx, ecx
    jz .empty_array      

    
    cmp ebp, edx         
    jg .output_odd    
    
.output_even:
    mov eax, esi        
    jmp .output
    
.output_odd:
    mov eax, edi      
    
.output:
    call printInt       
    call printEndl      
    xor rdi, rdi        
    jmp .exit_program

.empty_array:
    mov rdi, -1          

.exit_program:
    mov rax, 60          
    syscall              



    Enjoy Reading This Article?

    Here are some more articles you might like to read next:

  • Some points of Assembly Language 2024
  • Linux Basic Command Manual
  • DeltaConv:用于点云几何深度学习的各向异性算子
  • Доп. главы по Мат. Анализу
  • 吉米多维奇习题集 - 不定积分