Arduino не входит в прерывание конечных точек

vladsf
Offline
Зарегистрирован: 30.03.2021

Прошу помощи у знающих людей. Сломал всю голову. Не могу добиться, что бы срабатывали прерывания от конечных точек. Контроллер отказывается в них входить, хотя в Протеусе все нормально
Вот часть кода.

.Cseg
.org $0000
jmp rese;
; ***** INTERRUPT VECTORS ************************************************
;.org    INT0addr;  = 0x0002    ; External Interrupt Request 0
;rjmp   INT0address
;.org   INT1addr;   = 0x0004    ; External Interrupt Request 1
;rjmp   INT1address
;.org   INT2addr;   = 0x0006    ; External Interrupt Request 2
;rjmp   INT2address
;.org   INT3addr;   = 0x0008    ; External Interrupt Request 3
;rjmp   INT3address
;.org   Reserved1addr;  = 0x000a    ; Reserved1
;rjmp   Reserved1address
;.org   Reserved2addr;  = 0x000c    ; Reserved2
;rjmp   Reserved2address
;.org   INT6addr;   = 0x000e    ; External Interrupt Request 6
;rjmp   INT6address
;.org   Reserved3addr;  = 0x0010    ; Reserved3
;rjmp   Reserved3address
;.org   PCI0addr;   = 0x0012    ; Pin Change Interrupt Request 0
;rjmp   PCI0address
.org    USB_GENaddr;    = 0x0014    ; USB General Interrupt Request
jmp   USB_GENaddress 
.org    USB_COMaddr;    = 0x0016    ; USB Endpoint/Pipe Interrupt Communication Request
jmp   USB_COMaddress
;.org   WDTaddr;    = 0x0018    ; Watchdog Time-out Interrupt
;rjmp   WDTaddress
;.org   Reserved4addr;  = 0x001a    ; Reserved4
;rjmp   Reserved4address 
;.org   Reserved5addr;  = 0x001c    ; Reserved5
;rjmp   Reserved5address
;.org   Reserved6addr;  = 0x001e    ; Reserved6
;rjmp   Reserved6address
;.org   ICP1addr;   = 0x0020    ; Timer/Counter1 Capture Event
;rjmp   ICP1address
.org    OC1Aaddr;   = 0x0022    ; Timer/Counter1 Compare Match A
jmp   OC1Aaddress
;.org   OC1Baddr;   = 0x0024    ; Timer/Counter1 Compare Match B
;rjmp   OC1Baddress
;.org   OC1Caddr;   = 0x0026    ; Timer/Counter1 Compare Match C
;rjmp   OC1Caddress
;.org   OVF1addr;   = 0x0028    ; Timer/Counter1 Overflow
;rjmp   OVF1address
;.org   OC0Aaddr;   = 0x002a    ; Timer/Counter0 Compare Match A
;rjmp   OC0Aaddress
;.org   OC0Baddr;   = 0x002c    ; Timer/Counter0 Compare Match B
;rjmp   OC0Baddress
;.org   OVF0addr;   = 0x002e    ; Timer/Counter0 Overflow
;rjmp   OVF0address
;.org   SPIaddr;    = 0x0030    ; SPI Serial Transfer Complete
;rjmp   SPIaddress
;.org   URXC1addr;  = 0x0032    ; USART1, Rx Complete
;rjmp   URXC1address
;.org   UDRE1addr;  = 0x0034    ; USART1 Data register Empty
;rjmp   UDRE1address
;.org   UTXC1addr;  = 0x0036    ; USART1, Tx Complete
;rjmp   UTXC1address
;.org   ACIaddr;    = 0x0038    ; Analog Comparator
;rjmp   ACIaddress
.org    ADCCaddr;   = 0x003a    ; ADC Conversion Complete
jmp    ADCCaddress
;.org   ERDYaddr;   = 0x003c    ; EEPROM Ready
;rjmp   ERDYaddress
;.org   ICP3addr;   = 0x003e    ; Timer/Counter3 Capture Event
;rjmp   ICP3address
.org    OC3Aaddr;   = 0x0040    ; Timer/Counter3 Compare Match A
jmp   OC3Aaddress
;.org   OC3Baddr;   = 0x0042    ; Timer/Counter3 Compare Match B
;rjmp   OC3Baddress
;.org   OC3Caddr;   = 0x0044    ; Timer/Counter3 Compare Match C
;rjmp   OC3Caddress
;.org   OVF3addr;   = 0x0046    ; Timer/Counter3 Overflow
;rjmp   OVF3address
;.org   TWIaddr;    = 0x0048    ; 2-wire Serial Interface
;rjmp   TWIaddress
;.org   SPMRaddr;   = 0x004a    ; Store Program Memory Read
;rjmp   SPMRaddress
;.org   SPMRaddr;   = 0x004c    ; Timer/Counter4 Compare Match A
;rjmp   SPMRaddress
;.org   OC4Baddr;   = 0x004e    ; Timer/Counter4 Compare Match B
;rjmp   OC4Baddress
;.org   OC4Daddr;   = 0x0050    ; Timer/Counter4 Compare Match D
;rjmp   OC4Daddress
;.org   OVF4addr;   = 0x0052    ; Timer/Counter4 Overflow
;rjmp   OVF4address
;.org   OVF4addr;   = 0x0054    ; Timer/Counter4 Fault Protection Interrupt
;rjmp   OVF4address
;.org   INT_VECTORS_SIZE    ;= 86   ; size in words
;rjmp   INT_VECTORS_SIZEess
 
 
;********************************************************************
.def prom1 =r20; промежуточный регистр 1 
.def prom2 =r21; промежуточный регистр 2
.def prom3 =r22; промежуточный регистр 3 
.def prom4 =r23; промежуточный регистр 4
.def prom5 =r24; промежуточный регистр 5 
.def schetchik =r25; промежуточный регистр 6
.Cseg
.org $d0
 
 
rese:
ldi prom1, low(ramend)
out spl, prom1
ldi prom1, high(ramend)
out sph, prom1
cli
......................
sei
 
 
loop:
 
rjmp loop
 
init_USB_DEVICE:
............................
;Usb_select_endpoint(EP_CONTROL = 0)
ldi r16,0
sts UENUM,r16           ; Выбираем EndPoint 0 (мало ли что там случилось)
lds r16, UEIENX
ldi r23, RXSTPE; разрешение прерывания по setup pacet
call wybor_bit_or
sts UEIENX,r16
lds r16, UEIENX
ldi r23, RXOUTE; разрешение прерывания по приему данных
call wybor_bit_or
sts UEIENX,r16
;lds r16, UEIENX
;ldi r23, TXINE; разрешение прерывания по передаче данных
;call wybor_bit_or
;sts    UEIENX,r16
SB_wait_vbus:
LDS R16,USBSTA          
SBRS    R16,VBUS            ; Если на ноге VBUS устаканилось напряжение, продолжаем
;ret
rjmp    USB_wait_vbus
lds r16, UDCON
ldi r23, DETACH
call wybor_bit_and
ldi r23, LSM
call wybor_bit_and
sts UDCON, r16
ret
 
 
 
 
 
USB_COMaddress:
in r10, sreg
push r16
push r17
push r18
push r19
push r20
push r21
push r22
push r23
push r24
push r25
push r26
push r27
push r28
push r29
push r30
push r31
 
 
 
call USB_Decriptor
 
 
 
pop r31
pop r30
pop r29
pop r28
pop r27
pop r26
pop r25
pop r24
pop r23
pop r22
pop r21
pop r20
pop r19
pop r18
pop r17
pop r16
out sreg, r10
reti
b707
Offline
Зарегистрирован: 26.05.2017

хотите, чтобы кто-то обратил внимание на ваш вопрос - выкладывайте код правильно

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

1. Вставка программного кода в тему/комментарий

2. Поясните, пожалуйста, что такое "прерывания от конечных точек"?

vladsf
Offline
Зарегистрирован: 30.03.2021

Подскажите, как правильно

vladsf
Offline
Зарегистрирован: 30.03.2021

Прерывания, которые вызывают установку флагов RXTSPI, RXOUTE и т.д.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

Фига-се. Может быть в таком случае, Вы, кроме правильной вставки полного (а не огрызка) кода, ещё и скажете какой у Вас контроллер? Или нам угадывать надо?

vladsf
Offline
Зарегистрирован: 30.03.2021

Такой же как в Ардуино - atmega32u4

wdrakula
wdrakula аватар
Offline
Зарегистрирован: 15.03.2016

vladsf пишет:

Такой же как в Ардуино - atmega32u4

В какой Ардуино?

На 32U4 сделано две платы - Леонардо и Микро, из полутора десятков. Самые распространенные платы - Ардуино Нано и Уно - сделаны за Atmega 328p. Это раз.

И два: В приведенном ассемблерном куске не содержится вообще ничего содержательного (милая тавтология ;) ). Никакого осмысленного кода.

И три: 32К памяти + 2.5К ОЗУ + 16 МГц требуют кода на ассемблере для какой-то задачи? Или это попытка показать себя? ;))))))

 

Komandir
Komandir аватар
Offline
Зарегистрирован: 18.08.2018

Если вы не в состоянии правильно вставить код в форум, то зачем вы лезете в ассемблер ?

Ваш код НИЧЕГО кроме установки указателя стека не делает !

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

Komandir пишет:

Ваш код НИЧЕГО кроме установки указателя стека не делает !

Как это ничего? А кто засирает 10-ый регистр в ISR?

vladsf
Offline
Зарегистрирован: 30.03.2021

Моя плата Ардуино называется pro micro. Собрана на базе контроллера atmega32u4. Память 32кБт, тактовая частота 16МГц. Все как обычно. С Ардуино я новичок. Занимаюсь с китайским чудом, где-то две недели сразу как пришла посылка. Первое, что подумал, а как стереть прошивку ардуино и залить свою. В первые же 15 минут одну ардуино залочил. Потом долго мучался, чтобы ее восстановить, думал попрощался с платой.

Затем решил разработать на базе ардуино CDC устройство для USB. Неделя мучений и о чудо устройство стало обмениваться данными с компьютером. Единственный косяк получать от хоста USB дескрипторы приходится в теле программы, а удобнее, чтобы не возникали таймауты через прерывания. Для этих целей и есть прерывания конечных точек USb_Comadress. В Протеусе к слову сказать код работает. Подумалось случаем не косяк в китайском железе. Сэкономили на этом прерывании.

И делаю все вроде бы правильно. В таблице векторов прерывание есть.

.Cseg
.org $0000
jmp rese;
; ***** INTERRUPT VECTORS ************************************************

.org	USB_GENaddr;	= 0x0014	; USB General Interrupt Request
jmp   USB_GENaddress 
.org	USB_COMaddr;	= 0x0016	; USB Endpoint/Pipe Interrupt Communication Request
jmp   USB_COMaddress
.org	ADCCaddr;	= 0x003a	; ADC Conversion Complete
jmp    ADCCaddress
.org	OC3Aaddr;	= 0x0040	; Timer/Counter3 Compare Match A
jmp   OC3Aaddress
;.org	INT_VECTORS_SIZE	;= 86	; size in words
;rjmp   INT_VECTORS_SIZEess


;********************************************************************
.def prom1 =r20; промежуточный регистр 1 
.def prom2 =r21; промежуточный регистр 2
.def prom3 =r22; промежуточный регистр 3 
.def prom4 =r23; промежуточный регистр 4
.def prom5 =r24; промежуточный регистр 5 
.def schetchik =r25; промежуточный регистр 6
.Cseg
.org $d0


rese:
ldi prom1, low(ramend)
out spl, prom1
ldi prom1, high(ramend)
out sph, prom1

В подпрограмме инициализации выставляю в регистрах нужные биты для разрешения прерываний

lds r16, UEIENX
ldi r23, RXSTPE; разрешение прерывания по setup pacet
call wybor_bit_or; установка нужного бита
sts	UEIENX,r16
lds r16, UEIENX
ldi r23, RXOUTE; разрешение прерывания по приему данных
call wybor_bit_or; установка нужного бита
;sts	UEIENX,r16

Глобально разрешаю  все прерывания, а контроллер в его не входит

USB_COMaddress:
in r10, sreg
push r16
push r17
push r18
push r19
push r20
push r21
push r22
push r23
push r24
push r25
push r26
push r27
push r28
push r29
push r30
push r31


call USB_Decriptor



pop r31
pop r30
pop r29
pop r28
pop r27
pop r26
pop r25
pop r24
pop r23
pop r22
pop r21
pop r20
pop r19
pop r18
pop r17
pop r16
out sreg, r10
reti

Извините может сумбурно. Весь код не привожу, потому что он большой и работает с той разницей лишь, что я опрашиваю флаги RXstpi, Rxoute для получения дескрипторов в теле программы, а не в прерывании.

sadman41
Offline
Зарегистрирован: 19.10.2016

Сэкономили на этом прерывании(C)

Сколько, интересно, в юанях?

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

1.
С чего сделан вывод, что 

vladsf пишет:

контроллер в его не входит

какие именно тесты на это указывают? Я, например, не вижу в обработчике прерывания попытки подать сигнал, что оно туда вошло (светодиод зажечь, например).

2.
Из каких соображений Вы загаживаете регистр 10 в обработчике прерывания и не восстанавливаете его?

3.
После заявлений типа

vladsf пишет:
Весь код не привожу

обычно следует ответ: тогда разбирайтесь сами.

Искать ошибки в коде, не видя его, я не умею.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

sadman41 пишет:
Сэкономили на этом прерывании(C) Сколько, интересно, в юанях?
Поллитра!

vladsf
Offline
Зарегистрирован: 30.03.2021

Хорошо пошутил.

 

vladsf
Offline
Зарегистрирован: 30.03.2021

1. Здесь в коде, а так зажигаю светодиод подключенный к PD5. В Протеусе загорается, а в железе нет. Из этого делают вывод, что в прерывание не входит, ну а дальше дескрипторы не обрабатываются и устройство определяется, как неопознанное.

2. Просто я так привык к своим кодам. Сила привычки. R10 использую только по регистр статуса. Но это к прерываниям дела не имеет.

3. Я пишу, что код большой, но по моему вход в прерывание определяется, только выжимками из кода.

Хотя полную версию я сделаю, чуть позже.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

vladsf пишет:

1. Здесь в коде, а так зажигаю светодиод подключенный к PD5. 

Ну, вот, видите, а мне-то это откуда знать? И откуда мне знать, что Вы там ещё делаете или не делаете?

vladsf
Offline
Зарегистрирован: 30.03.2021

Ну если я писал, что через прерывание, не работает, через флаги все ок. Значит я менял код , я же не могу все версии привести. Вы не можете привести пример, как войти в прерывание.

vladsf
Offline
Зарегистрирован: 30.03.2021

Выкладываю код.

.include "m32U4def.inc"
.device atmega32U4
.Cseg
.org $3f30
T_DescriptorDevice:
Descriptor_Device_standart:
.db 0x12, 0x01;
.db 0x10, 0x01;
.db 0x02, 0
.db 0, 0x40
.db 0xeb, 0x03;
.db 0x09, 0x20;
.dw 00
.db 0, 0
.db 0

Descriptor_Device_Configuration1:
.db 0x09, 02
.db 0x43, 0x00
.db 2, 1
.db 0, 0x80
.db 0x50, $09
.db 4, 0
.db 0, 1
.db 2, 2
.db 1, 0

.db 0x05, 0x24, 0x00, 0x10 
.db 0x01, 0x05, 0x24, 0x01, 0x03, 0x01 
.db 0x04, 0x24, 0x02, 0x06       
.db 0x05, 0x24, 0x06, 0x00
.db 0x01, 7 

.db 5, 0x83, 3, 0x40
.db 0x00, 0

.db 9, 4, 1, 0, 2, 0xa
.db 0, 0, 0, 7

.db 5, 1, 2, 0x40, 0x00, 0
.db  7, 3;

.db   0x82, 2, 0x40, 0x00
.db  0, 0 


Descriptor_Device_String1:
.db $4, 3
.db 'V', $00


Descriptor_Device_String2:
.db $4, 3
.db 'D', $00



Descriptor_Device_String3:

.db $04, 3
.db 'V', $00


Descriptor_Device_String0:
.db $04, 3
.db $09, $04

.Cseg
.org $0000
jmp rese;
; ***** INTERRUPT VECTORS ************************************************

.org	USB_GENaddr;	= 0x0014	; USB General Interrupt Request
jmp   USB_GENaddress 
.org	USB_COMaddr;	= 0x0016	; USB Endpoint/Pipe Interrupt Communication Request
jmp   USB_COMaddress
.org	OC1Aaddr;	= 0x0022	; Timer/Counter1 Compare Match A
jmp   OC1Aaddress
.org	ADCCaddr;	= 0x003a	; ADC Conversion Complete
jmp    ADCCaddress
.org	OC3Aaddr;	= 0x0040	; Timer/Counter3 Compare Match A
jmp   OC3Aaddress



;********************************************************************
.def prom1 =r20; ïðîìåæóòî÷íûé ðåãèñòð 1 
.def prom2 =r21; ïðîìåæóòî÷íûé ðåãèñòð 2
.def prom3 =r22; ïðîìåæóòî÷íûé ðåãèñòð 3 
.def prom4 =r23; ïðîìåæóòî÷íûé ðåãèñòð 4
.def prom5 =r24; ïðîìåæóòî÷íûé ðåãèñòð 5 
.def schetchik =r25; ïðîìåæóòî÷íûé ðåãèñòð 6
.Cseg
.org $d0
rese:
ldi prom1, low(ramend)
out spl, prom1
ldi prom1, high(ramend)
out sph, prom1


cli ; ãëîáàëüíîå çàïðåùåíèå ïðåðûâàíèé
ldi prom1, $f1; 
out ddrb, prom1
ldi prom1, $00; 
out portb, prom1
ldi prom1, $ff;
out ddrd, prom1
ldi prom1, $00; 
out portd, prom1
sbi portb, $0
sbi portd, $5
ldi prom1, $40;
out ddre, prom1
ldi prom1, $04;    
out porte, prom1
ldi prom1, $40;
out ddrc, prom1
ldi prom1, $00;    
out portc, prom1


ldi prom1, $00;
out ddrf, prom1
ldi prom1, $70;   
out portf, prom1

ldi prom1, $f0
mov r6, prom1
ldi prom1, $0f
mov r7, prom1
ldi prom1, $00
mov r8, prom1

program:

ldi prom1, $00
sts tccr1A, prom1 
ldi prom1, $09
sts tccr1B, prom1  
ldi prom1, $00
sts tccr1C, prom1  
ldi prom1, $00
sts ocr1ah, prom1
ldi prom1, $9f
sts ocr1al, prom1
ldi prom1, $02;
sts timsk1, prom1   

ldi prom1, $00;
sts tccr3A, prom1   
ldi prom1, $09; 
sts tccr3B, prom1   
ldi prom1, $00;
sts tccr3C, prom1   
ldi prom1, $3e;
sts ocr3ah, prom1
ldi prom1, $7f;
sts ocr3al, prom1
ldi prom1, $02
sts timsk3, prom1

ldi prom1, $01;
mov r5, prom1
sts $100, r8
ldi prom1, $ff
mov r9, prom1
mov r15, prom1


ldi prom1, $47
sts admux, prom1
ldi prom1, $00;
sts adcsrb, prom1 
cbi portd, $5
call init_USB_DEVICE
sts $240, r7
sei;
loop:
LDS	R16, USBSTA			
SBRS	R16,VBUS			
rjmp	USB_stop
rjmp iniz_usb_ok
USB_stop:
sts $202, r7
rjmp daleee
iniz_usb_ok:
lds prom1, $202
cpi prom1, $f0
breq no_iniz_USB
sts $202, r6
lds r16, UDCON
ldi r23, DETACH
call wybor_bit_and
ldi r23, LSM
call wybor_bit_and
sts	UDCON, r16

no_iniz_USB:
daleee:
;sts $240, r6
rjmp timer_mini


USB_Decriptor:
wait_req_setup:
ldi	r16,0
sts	UENUM,r16
LDS	R16,UEINTX
SBRS	R16,RXSTPI
ret
lds r17,UEDATX ; 
lds r18,UEDATX ; 
lds r19,UEDATX ; 
lds r20,UEDATX ; 
lds r21,UEDATX ; 
lds r22,UEDATX ; 
lds XL,UEDATX ; 
lds XH,UEDATX ; 
cpi R18,0x06
breq GetDescriptor
cpi R18,0x05
brne no_SetAddress
rjmp SetAddress_run
no_SetAddress:
cpi r18,0x09
brne no_SetGonfiguration
rjmp SetGonfiguration;
no_SetGonfiguration:
cpi r18,0x21;
brne no_GetInterface2
rjmp GetInterface
no_GetInterface2:
cpi r18,0x22;
brne no_GetInterface3
rjmp GetInterface
no_GetInterface3:
cpi r18,0x20;
brne no_GetInterface4
rjmp GetInterface
no_GetInterface4:

ret

GetDescriptor:
CPI R17,0x80
breq GetDescriptorStandart
CPI R17,0x81
breq GetDescriptorUser
cli
GetDescriptorStandart:
CPI R20,0x01 ; 
brne GDS1
ldi ZH,High(Descriptor_Device_standart*2) ;
ldi ZL,Low (Descriptor_Device_standart*2) ;
ldi YH, $00
ldi YL, $12
rjmp GetDescriptorData
GDS1:
cpi r20,0x02 ; 
brne GDS2
ldi ZH,High(Descriptor_Device_Configuration1*2) ;
ldi ZL,Low (Descriptor_Device_Configuration1*2) ;
ldi YH, $00
ldi YL, $43;09;20
rjmp GetDescriptorData
GDS2:
CPI R20,0x03 ; 
brne GDS3
CPI R19,0x00 ;
brne GDS2_1
ldi ZH,High(Descriptor_Device_String0*2) ;
ldi ZL,Low (Descriptor_Device_String0*2) ;
ldi YH, $00
ldi YL, $04
rjmp GetDescriptorData
GDS2_1:
CPI R19,0x01 ; 
brne GDS2_2
ldi ZH,High(Descriptor_Device_String1*2) ;
ldi ZL,Low (Descriptor_Device_String1*2) ;
ldi YH, $00
ldi YL, $4;28
rjmp GetDescriptorData
GDS2_2:
CPI R19,0x02 ; 
brne GDS2_3
ldi ZH,High(Descriptor_Device_String2*2) ;
ldi ZL,Low (Descriptor_Device_String2*2) ;
ldi YH, $00
ldi YL, $4;32
rjmp GetDescriptorData
GDS2_3:
CPI R19,0x03 ; 
brne GDS2_4
ldi ZH,High(Descriptor_Device_String3*2) ;
ldi ZL,Low (Descriptor_Device_String3*2) ;
ldi YH, $00
ldi YL, $04
rjmp GetDescriptorData
GDS2_4:
RET

GDS3:
ret;

GetDescriptorUser:
CPI r20,0x21
breq xxxxxxxxxxx
CPI r20,0x22
breq hid_get_report_descriptor
xxxxxxxxxxx:
ret
hid_get_report_descriptor:
ldi ZH,High(Descriptor_Device_String3*2) ;
ldi ZL,Low (Descriptor_Device_String3*2) ;
ldi YH, $00
ldi YL, $3b
rjmp GetDescriptorData

GetInterface:
CPI R17,0x81
breq xxxxxxxxxxx
cpi r17,0xA1;21
breq Set_Class_Inter
cpi r17,0x21
breq Set_Class_dan
ret
Set_Class:

Set_Class_dan:
SCI1d:
lds r16, UEINTX
ldi r23, RXSTPI
call wybor_bit_and
sts	UEINTX, r16
lds r16, UEINTX
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
SCIDAN:
LDS R24,UEINTX
SBRS R24,TXINI
RJMP SCIDAN
ret
Set_Class_Inter:
lds r16, UEINTX
ldi r23, RXSTPI
call wybor_bit_and
sts	UEINTX, r16
lds r16, UEINTX
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
SCII:
LDS R24,UEINTX
SBRS R24,TXINI
RJMP SCII
ret
SetGonfiguration:
cpi r17,0
breq SC1
cpi r17,0x21
brne no_SetConfInterface
rjmp SetConfInterface
no_SetConfInterface:
SC1:
cpi r19,0x01
breq SetConfAddressed

SetConfAddressed:
lds r16, UEINTX
ldi r23, RXSTPI
call wybor_bit_and
sts	UEINTX, r16
lds r16, UEINTX; 
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
SCA:
LDS R24,UEINTX
SBRS R24,Txini;
RJMP SCA
call ep1_iniz
call ep2_iniz
call ep3_iniz
ret

ep1_iniz:
ldi r16,$01
sts UENUM,r16; 
ldi r16,0x01
sts UECONX,r16;
ldi r16,0x80; 
STS UECFG0X,r16
ldi r16,0X30;
sts UECFG1X,r16
lds r16, UECFG1X
ldi r23, ALLOC
call wybor_bit_or
sts	UECFG1X, r16
USB_wait_vbus11:
LDS R16,UESTA0X
SBRS R16,CFGOK ; 
RJMP USB_wait_vbus11
ret

ep2_iniz:
ldi r16,0X02; 
sts UENUM,r16
ldi r16,0x01; 
sts UECONX,r16
ldi r16,0x81 ; 
STS UECFG0X,r16
ldi r16,0X30;
sts UECFG1X,r16
lds r16, UECFG1X
ldi r23, ALLOC
call wybor_bit_or
sts	UECFG1X, r16
USB_wait_vbus12:
LDS R16,UESTA0X
SBRS R16,CFGOK 
RJMP USB_wait_vbus12
ret

ep3_iniz:
ldi r16,0X03; 
sts UENUM,r16
ldi r16,0x01; 
sts UECONX,r16
ldi r16,0xc1 ; 
STS UECFG0X,r16
ldi r16,0X30
sts UECFG1X,r16
lds r16, UECFG1X
ldi r23, ALLOC
call wybor_bit_or
sts	UECFG1X, r16
USB_wait_vbus13:
LDS R16,UESTA0X
SBRS R16,CFGOK ;
RJMP USB_wait_vbus13
ret



SetConfInterface:
lds r16, UEINTX
ldi r23, RXSTPI
call wybor_bit_and
sts	UEINTX, r16
lds r16, UEINTX
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
SCIF1:
LDS R24,UEINTX
SBRS R24,Txini
RJMP SCIF1
ret
lds r16, UEINTX
ldi r23, RXSTPI
call wybor_bit_and
sts	UEINTX, r16
lds r16, UEINTX
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
SCIF2:
LDS R24,UEINTX
SBRS R24,Txini;
RJMP SCIF2

ret

ServiceUSB :
ldi ZH,High(T_DescriptorDevice*2) 
ldi ZL,Low (T_DescriptorDevice*2) 
ldi YH, $00
ldi YL, $12
GetDescriptorData:
mov r24, r8
lds r16, UEINTX
ldi r23, RXSTPI
call wybor_bit_and
sts	UEINTX, r16
	cp	XL,YL				; 
	cpc	XH,YH			; 
	brlo	GDD0				; 
	mov	XL,YL
	mov	XH,YH
GDD0:						; 
	LDS	R16,UEINTX     		;
	SBRS	R16,TXINI			;
	RJMP	GDD0

GDD1:
	LPM	r16,Z+          			; 
	sts	UEDATX,r16
	inc r24
	cpi r24, $40
	brsh perepolnenie_64byte
	sbiw	X,1
	brne	GDD1
ppp:
lds r16, UEINTX
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
GDD2:
	LDS	R16,UEINTX     	; 
	SBRS	R16,RXOUTI		;  
	RJMP	GDD2			; 
lds r16, UEINTX
ldi r23, RXOUTI
call wybor_bit_and
sts	UEINTX, r16
lds r16, UEINTX
ldi r23, NAKOUTI
call wybor_bit_and
sts	UEINTX, r16
ret
perepolnenie_64byte:
lds r16, UEINTX
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
GDD0p:						
	LDS	R16,UEINTX     		;
	SBRS	R16,TXINI			;
	RJMP	GDD0p
pp:
	LPM	r16,Z+          			
	sts	UEDATX,r16
	sbiw	X,1
	brne	pp
rjmp ppp


SetAddress_run:
	TST	R17       		    
	BREQ	SetAddress1
	RJMP	SetAddress3
SetAddress1:
	andi	r19,0x7F		; 
	sts	UDADDR,r19     
lds r16, UEINTX
ldi r23, RXSTPI
call wybor_bit_and
sts	UEINTX, r16
lds r16, UEINTX
ldi r23, TXINI
call wybor_bit_and
sts	UEINTX, r16
SetAddress2:
	LDS	R24,UEINTX
	SBRS	R24,TXINI   	
	RJMP	SetAddress2
lds r16, UDADDR
ldi r23, ADDEN
call wybor_bit_or
sts	UDADDR, r16
SetAddress3:
ret

wybor_bit_or:
cpi r23, $00
breq bit_0_or
cpi r23, $01
breq bit_1_or
cpi r23, $02
breq bit_2_or
cpi r23, $03
breq bit_3_or
cpi r23, $04
breq bit_4_or
cpi r23, $05
breq bit_5_or
cpi r23, $06
breq bit_6_or
cpi r23, $07
breq bit_7_or
ret
bit_0_or:
ldi r23, $01
or r16, r23
ret
bit_1_or:
ldi r23, $02
or r16, r23
ret
bit_2_or:
ldi r23, $04
or r16, r23
ret
bit_3_or:
ldi r23, $08
or r16, r23
ret
bit_4_or:
ldi r23, $10
or r16, r23
ret
bit_5_or:
ldi r23, $20
or r16, r23
ret
bit_6_or:
ldi r23, $40
or r16, r23
ret
bit_7_or:
ldi r23, $80
or r16, r23
ret

wybor_bit_and:
cpi r23, $00
breq bit_0_and
cpi r23, $01
breq bit_1_and
cpi r23, $02
breq bit_2_and
cpi r23, $03
breq bit_3_and
cpi r23, $04
breq bit_4_and
cpi r23, $05
breq bit_5_and
cpi r23, $06
breq bit_6_and
cpi r23, $07
breq bit_7_and
ret
bit_0_and:
ldi r23, $fe
and r16, r23
ret
bit_1_and:
ldi r23, $fd
and r16, r23
ret
bit_2_and:
ldi r23, $fb
and r16, r23
ret
bit_3_and:
ldi r23, $f7
and r16, r23
ret
bit_4_and:
ldi r23, $ef
and r16, r23
ret
bit_5_and:
ldi r23, $df
and r16, r23
ret
bit_6_and:
ldi r23, $bf
and r16, r23
ret
bit_7_and:
ldi r23, $7f
and r16, r23
ret

init_USB_DEVICE:
lds r16, Clkpr
ldi r23, CLKPCE
call wybor_bit_or;and
sts Clkpr, r16
clr	r16
sts	CLKPR,r16			;
lds r16, UHWCON
ldi r23, UVREGE
call wybor_bit_or;and
sts	UHWCON,r23
lds r16, USBCON
ldi r23, USBE
call wybor_bit_and
sts	USBCON,r16
ldi r23, OTGPADE
call wybor_bit_and
sts	USBCON,r16
lds r16, UDCON
ldi r23, DETACH
call wybor_bit_or
sts	UDCON,r16
in r16, PLLCSR
ldi r23, plle
call wybor_bit_and
in r16, PLLCSR
ldi r23, pindiv
call wybor_bit_or
out	PLLCSR, r16;
in r16, PLLFRQ
ldi r23, pinmux
call wybor_bit_and
out	PLLFRQ,r16
in r16, PLLFRQ
ldi r23, pllusb
call wybor_bit_and
out	PLLFRQ,r16
in r16, PLLFRQ
ldi r23, PLLTM1
call wybor_bit_or
ldi r23, PLLTM0
call wybor_bit_or
out	PLLFRQ, r16
in r16, PLLFRQ
ldi r23, pdiv3
call wybor_bit_and
ldi r23, pdiv2
call wybor_bit_or
ldi r23, pdiv1
call wybor_bit_and
ldi r23, pdiv0
call wybor_bit_and
out	PLLFRQ, r16
in r16, PLLCSR
ldi r23, PLLE
call wybor_bit_or
out	PLLCSR,r16
PLL_START:
IN	R0,PLLCSR       
SBRS	R0,PLOCK           			
RJMP	PLL_START
lds r16, USBCON
ldi r23, USBE
call wybor_bit_or
ldi r23, OTGPADE
call wybor_bit_or
sts	USBCON,r16
lds r16, USBCON
ldi r23, FRZCLK
call wybor_bit_and
sts	USBCON,r16
call ep0_iniz
lds r16, UDIEN
ldi r23, EORSTE
call wybor_bit_or
sts	UDIEN,r16
ldi	r16,0
sts	UENUM,r16			; Âûáèðàåì EndPoint 0 (ìàëî ëè ÷òî òàì ñëó÷èëîñü)
lds r16, UEIENX
ldi r23, RXSTPE; ðàçðåøåíèå ïðåðûâàíèÿ ïî setup pacet
call wybor_bit_or
sts	UEIENX,r16
lds r16, UEIENX
ldi r23, RXOUTE; ðàçðåøåíèå ïðåðûâàíèÿ ïî ïðèåìó äàííûõ
call wybor_bit_or
sts	UEIENX,r16
ret




timer_mini:
call timer_mini_kacheli_foll
rjmp loop


timer_mini_kacheli_foll:
ldi prom1, $87;a0;
ldi prom2, $13;10;ec;13;09;13
clc
sub prom1, r9;r16
sbc prom2, r15
brcs chet_50ms_run
ret




chet_50ms_run:;cbi portb, $5
ldi prom1, $ff
mov r9, prom1
mov r15, prom1
lds prom1, $240
cpi prom1, $0f
breq pinb0_1_0
sbis pinb, $0
rjmp pinb0_1
cbi portb, $0
rjmp pinb0_1_0
pinb0_1:
sbi portb, $0
pinb0_1_0:
call azp
lds prom1, $200
cpi prom1, $13
brsh imp_sec_ok
inc prom1
sts $200, prom1
ret
imp_sec_ok:
sts $200, r8
ret

ep0_iniz:
ldi	r16,0
sts	UENUM,r16		
lds r16, UECONX
ldi r23, EPEN
call wybor_bit_or
sts	UECONX,r16
ldi	r16,0x00
sts	UECFG0X,r16		
ldi	r16,0x00
sts	UECFG1X,r16		; 
lds r16, UECFG1X
ldi r23, $4
call wybor_bit_or
ldi r23, $5
call wybor_bit_or
ldi r23, $6
call wybor_bit_and
sts	UECFG1X,r16
lds r16, UECFG1X
ldi r23, ALLOC
call wybor_bit_or
sts	UECFG1X,r16
USB_wait_vbus10:
LDS R16,UESTA0X
SBRS R16,CFGOK 
RJMP USB_wait_vbus10
ret

USB_GENaddress:
in r10, sreg
push r16
push r23

LDS	R16, UDINT
sbrs r16, EORSTI
rjmp exit_endpoint
ldi r16, $00
sts	UERST, r16
lds r16, UDINT
ldi r23, EORSTI
call wybor_bit_and
sts	UDINT, r16
call ep0_iniz
exit_endpoint:
pop r23
pop r16
out sreg, r10
reti


USB_COMaddress:
in r10, sreg
push r16
push r17
push r18
push r19
push r20
push r21
push r22
push r23
push r24
push r25
push r26
push r27
push r28
push r29
push r30
push r31
call USB_Decriptor
sts $240, r6
pop r31
pop r30
pop r29
pop r28
pop r27
pop r26
pop r25
pop r24
pop r23
pop r22
pop r21
pop r20
pop r19
pop r18
pop r17
pop r16
out sreg, r10
reti




OC3Aaddress:
in r10, sreg
push prom1
push prom2
in prom1, pinf
andi prom1, $60
lds prom2, $2ab
cp prom1, prom2
brne analiz_chet
cpi prom1, $60
breq null_encoder
sts $2ab, prom1
pop prom2
pop prom1
out sreg, r10
reti
null_encoder:
sts $2ab, prom1
sts $2ac, prom1
pop prom2
pop prom1
out sreg, r10
reti

analiz_chet:
sts $2ab, prom1
lds prom2, $2ac
cpi prom2, $c0
breq chet_wprawo_ok 
cpi prom2, $20
breq chet_wlewo_ok 
clc
rol prom2
add prom2, prom1
sts $2ac, prom2
pop prom2
pop prom1
out sreg, r10
reti

chet_wprawo_ok :
sts $2ac, prom1
call encoder_minus
pop prom2
pop prom1
out sreg, r10
reti
chet_wlewo_ok: 
sts $2ac, prom1
call encoder_plus
pop prom2
pop prom1
out sreg, r10
reti


encoder_minus:
ret

zagolowki_plus:
ret
encoder_plus:
ret














wyx_oco_no_run:
push r16
push r17
push r18
push r19
push r20
push r21
push r22
push r23
push r24
push r25
push r26
push r27
push r28
push r29
push r30
push r31
call USB_Decriptor
pop r31
pop r30
pop r29
pop r28
pop r27
pop r26
pop r25
pop r24
pop r23
pop r22
pop r21
pop r20
pop r19
pop r18
pop r17
pop r16

pop prom4
pop prom3
pop prom2
pop prom1
out sreg, r10
reti

OC1Aaddress:
in r10, sreg
push prom1
push prom2
push prom3
push prom4
inc r9
brne no_inc_r15
inc r15
no_inc_r15:
cp r11, r7
breq wyx_oco_no_run
pop prom4
pop prom3
pop prom2
pop prom1
out sreg, r10
reti

ADCCaddress:
in r10, sreg
push r24
push r25

pop r25
pop r24
out sreg, r10
reti

azp:
ldi prom1, $c9
sts adcsra, prom1 
ret


b707
Offline
Зарегистрирован: 26.05.2017

а нафига это все через асм делать, интересно?

vladsf
Offline
Зарегистрирован: 30.03.2021

На ассемблере более гибкое программирование.

И кто как умеет.

mykaida
mykaida аватар
Offline
Зарегистрирован: 12.07.2018

vladsf пишет:

На ассемблере более гибкое программирование.

И кто как умеет.

Это Вы признались что си не знаете или вы-лись? Типа - "в этом г-не уж точно никто копаться не будет"?

b707
Offline
Зарегистрирован: 26.05.2017

vladsf пишет:

На ассемблере более гибкое программирование.

то есть то, что это на Си занимает 10-20 строк. а на АСМе - более 1000 - это называется "более гибко"?

mykaida
mykaida аватар
Offline
Зарегистрирован: 12.07.2018

Не, ну я понимаю, когда пишешь для тактовой частоты 32кГц с жестким таймкодом. Но в этой задаче на 16МГц какие проблемы?

Komandir
Komandir аватар
Offline
Зарегистрирован: 18.08.2018

Я понял почему не был показан код ...

Там ШЕДЕВРЫ  !!!!

wybor_bit_and: wybor_bit_or:

vladsf
Offline
Зарегистрирован: 30.03.2021

Мне нравится писать на ассемблере.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

vladsf пишет:

Выкладываю код.

Я Вас ещё утром об этом просил, но Вы всё сопротивлялись. А сейчас уже поздно, не могу этим заниматься. Мож другой кто, или в другой день.

Кстати, опишите как его запускать. Какую частоту выставить, что куда подсоединить. Что должно происходить. Как его запустить, в общем. Почему из Вас надо всё клещами тянуть?

vladsf
Offline
Зарегистрирован: 30.03.2021

Ну а как вы в регистре нужный бит установите или сбросите.

vladsf
Offline
Зарегистрирован: 30.03.2021

Хорошо, подожду.

Komandir
Komandir аватар
Offline
Зарегистрирован: 18.08.2018

Про сдвиговые операции не слышали ??? В 32 битном регистре будете 32 варианта перебирать ???

vladsf
Offline
Зарегистрирован: 30.03.2021

Вы имеете ввиду команды rol, ror. Приведите пример как например 6 бит установить, не повредив другие. Вообще кто, как привык, тот так и программирует.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

vladsf пишет:

Хорошо, подожду.

А второй абзац не прочитали? Ответ-то будет?

vladsf
Offline
Зарегистрирован: 30.03.2021

Давай до завтра. Просто сейчас интернет выключат, связи не будет.

andycat
andycat аватар
Offline
Зарегистрирован: 07.09.2017

vladsf пишет:

Приведите пример как например 6 бит установить, не повредив другие. 

x |= 0x40;

 

Logik
Offline
Зарегистрирован: 05.08.2014

vladsf пишет:

Давай до завтра. Просто сейчас интернет выключат, связи не будет.

8))

Спасибо что предупредил. Ща все файлы посохраняю..

mykaida
mykaida аватар
Offline
Зарегистрирован: 12.07.2018

andycat пишет:

x |= 0x40;

или x |= 1<<6;

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

b707 пишет:

а нафига это все через асм делать, интересно?

вот не надо завидовать )))

Komandir
Komandir аватар
Offline
Зарегистрирован: 18.08.2018
lds r16, UEIENX
ldi r23, RXSTPE
call wybor_bit_or
sts UEIENX,r16
lds r16, UEIENX
ldi r23, RXOUTE
call wybor_bit_or
sts UEIENX,r16

можно заменить на:

lds r16, UEIENX
ori r16,1<<RXSTPE+1<<RXOUTE
sts UEIENX,r16

 

b707
Offline
Зарегистрирован: 26.05.2017

да все, в турме прогулка закончилась, инет вырубили...

Morroc
Offline
Зарегистрирован: 24.10.2016

Тихо офигеваю... ))) ну не мог не написать чего нибудь, попкорна мало будет - нужно пицу заказать и за пивом сходить )

Задача побаловаться прерываниями и асм'ом что ли ?

-NMi-
Offline
Зарегистрирован: 20.08.2018

vladsf пишет:

Сила привычки. R10 использую только по регистр статуса. Но это к прерываниям дела не имеет.

Ачо именно r10?

И эта, наманые пасаны делают так:


push r10
in r10, sreg
push r10
...
...
pop r10
out sreg, r10
pop r10
reti

Правило очень простое - скока пушей --- стока попов!            )))))))))))))

DetSimen
DetSimen аватар
Offline
Зарегистрирован: 25.01.2017

-NMi- пишет:

Правило очень простое - скока пушей --- стока попов!            )))))))))))))

ой, не всегда.  Иногда, надо вернуться не туда, откуда вызвали, а забежать еще кой-куда по дороге, тогда пушишь на стек адрес, куда надо быстренько спрыгать и делаешь ret.  Скока ночей я GPF отлавливал с таким кодом, но научился в конце концов. :) 

-NMi-
Offline
Зарегистрирован: 20.08.2018

vladsf пишет:

Ну а как вы в регистре нужный бит установите или сбросите.

Твой любимый r10

выставим 5-й бит

ori r10, 0b00100000

сбросим 6 и 1-й биты

andi r10, 0b10111101

 

-NMi-
Offline
Зарегистрирован: 20.08.2018

DetSimen пишет:

 Иногда, надо вернуться не туда, откуда вызвали, а забежать еще кой-куда по дороге, тогда пушишь на стек адрес, куда надо быстренько спрыгать и делаешь ret. 

Это когда "попутный чипок" уже закрыли а дагнаццо надо? )))

vladsf
Offline
Зарегистрирован: 30.03.2021

Ваш код работать не будет

lds r16, UEIENX
02
	ldi r23, RXSTPE
03
	call wybor_bit_or
04
	sts UEIENX,r16
05
	lds r16, UEIENX
06
	ldi r23, RXOUTE
07
	call wybor_bit_or
08
	sts UEIENX,r16
09
	 
10
	можно заменить на:
11
	 
12
	lds r16, UEIENX
13
	ori r16,1<<RXSTPE+1<<RXOUTE
14
	sts UEIENX,r16


Наверное правильно так

lds r16, UEIENX
02
	ldi r23, RXSTPE
03
	call wybor_bit_or
04
	sts UEIENX,r16
05
	lds r16, UEIENX
06
	ldi r23, RXOUTE
07
	call wybor_bit_or
08
	sts UEIENX,r16
09
	 
10
	можно заменить на:
11
	 
12
	lds r16, UEIENX
13
	ori r16,1<<RXSTPE | 1<<RXOUTE
14
	sts UEIENX,r16

 А можно и в цикле , используя команды rol, ror

lds r16, UEINTX
ldi r23, $7;TXINI
ldi r22, $01
zikl_or:
cpi r23, $00
breq end_zikl_or
clc
rol r22
dec r23
rjmp zikl_or
end_zikl_or:
or r16, r22
sts	UEINTX, r16

lds r16, UEINTX
ldi r23, $7;TXINI
ldi r22, $7
clc
sub r23, r22
ldi r22, $fe
zikl_and:
cpi r23, $07
breq end_zikl_and
rol r22
inc r23
rjmp zikl_and
end_zikl_and:
and r16, r22
sts	UEINTX, r16

 

vladsf
Offline
Зарегистрирован: 30.03.2021

Так у меня также в подпрограммах делается, речь шла о командах rol, ror.

Komandir
Komandir аватар
Offline
Зарегистрирован: 18.08.2018

vladsf пишет:

Ваш код работать не будет

А проверить (прежде чем писать чушь) не судьба ?

Ваш "код" порождает разное число тактов, в зависимости от положения бита !

Вы же константы используете - пусть всё высчитывается на этапе перевода команд в машинный код, а не в процессе выполнения кода !!!

vladsf
Offline
Зарегистрирован: 30.03.2021

Прошивка записывается в ардуино. Старая стирается вместе с фьзами загрузчика. Тактовая частота 16МГц.

Код активизируется при подключении к USB порту компьютера и устройство начинает обмениваться дескрипторами. Подпрограмма init_USB настраивает USB ардуинки. Для вызова дескрипторов используется прерывание OC1Aaddress с тактом 10мКс, а по идее нужно через прерывание от конечных точек. В этом и заключаются мои грабли. Остальные прерывания не нужны, использовал как дежурные.

Если будешь запускать код, то поправь ветку, чтобы светодиод мигал. По частоте мигания светодиода оцениваю работу ардуино (зависла или работает).

chet_50ms_run:;cbi portb, $5
ldi prom1, $00
mov r9, prom1
mov r15, prom1

Про китайское железо хочу сказать следующее. Мне пришли две одинаковые ардуино. Так вот одна при отключение от USB при снятии синхронизации бит FRZCLK виснет, а другая нет. Хотя код один и тотже.

LDS	R16, USBSTA			
SBRS	R16,VBUS			; Если на ноге VBUS устаканилось напряжение, продолжаем
rjmp	USB_stop
rjmp iniz_usb_ok
USB_stop:

LDS	R16, UDINT
sbrs r16, SUSPI
rjmp daleee
lds r16, USBCON
ldi r23, FRZCLK
call wybor_bit_or
;sts	USBCON,r16
lds r16, UDINT
ldi r23, SUSPI
call wybor_bit_and
sts	UDINT, r16
rjmp daleee
iniz_usb_ok:
lds prom1, $202
cpi prom1, $f0
breq no_iniz_USB
sts $202, r6
;LDS	R16, UDINT
;sbrs r16, WAKEUPI
;rjmp no_iniz_USB
lds r16, USBCON
ldi r23, FRZCLK
call wybor_bit_and
sts	USBCON,r16
lds r16, UDCON
ldi r23, DETACH
call wybor_bit_and
ldi r23, LSM
call wybor_bit_and
sts	UDCON, r16
no_iniz_USB:
daleee:

За ранее благодарен если поможешь. Я склоняюсь к дефекту ардуино. Хотя обе ардуинки в плане прерывания ведут себя одинаково.

vladsf
Offline
Зарегистрирован: 30.03.2021

Проверил в Протеусе. Выдает вместо кода $0с код $40. Может протеус глючит, но мой код выдает все правильно.

vladsf
Offline
Зарегистрирован: 30.03.2021

Вы про команды rol и ror писали приведите пример, как в 32 разрядном регистре устанавливать и сбрасывать биты. Я привел , проверил все считает в AVR STUDIO.

vladsf
Offline
Зарегистрирован: 30.03.2021

В ассемблере вы оперируете напрямую с машинными командами и всегда можете упростить код, побороться за время выполнения, а в СИ за Вас это делает компилятор и не всегда корректно. У компилятора есть ограничения. Мне как то нужно было умножить два числа вида $FFFFFFFF. На СИ этого не получается, там ограничения в максимальном размере - $FFFF, а на ассемблере написал свою библиотеку и все считает