Picoblaze возвращается из ошибки прерывания - PullRequest
0 голосов
/ 18 мая 2018

у нас есть модуль bluetooth, который при изменении данных приемника посылает сигнал прерывания на пиктоплазму и понижает этот сигнал с подтверждением прерывания.Подпрограмма прерывания работает успешно, но система не может вернуть основную программу. Когда мы запускаем потоки основного цикла системы, как требуется, но после сигнала прерывания она застревает в подпрограмме прерывания. Мы можем вызывать подпрограмму прерывания снова и снова, но не можемвернитесь в основной цикл.

наш код сборки:

CONSTANT SONAR, 81
CONSTANT REMOTE, 82
CONSTANT MOTOR_R, 83
CONSTANT MOTOR_L, 84

CONSTANT ILERI, 00
CONSTANT SAG, 01
CONSTANT SOL, 02
CONSTANT SAGX, 03
CONSTANT SOLX, 04
CONSTANT ILERI2, 08
CONSTANT SAG2, 09
CONSTANT SOL2, 0A
CONSTANT SAGX2, 0B
CONSTANT SOLX2, 0C
CONSTANT HIZLAN, 05
CONSTANT YAVASLA, 06

NAMEREG sD, SPEED
NAMEREG sC, ENGELLER

LOAD sE, 00
LOAD SPEED, 3F  ; hiz degeri 0 ile 128 arasi degissin, main icinde degeri 
degisebilsin

ENABLE INTERRUPT

LOOP:

INPUT ENGELLER, 81

COMPARE ENGELLER, 1
JUMP NZ SOLSERBEST
CALL RIGHT
CALL DELAY_QS
JUMP LOOP

SOLSERBEST:

COMPARE ENGELLER, 2
JUMP NZ SAGSERBEST
CALL LEFT
CALL DELAY_QS
JUMP LOOP

SAGSERBEST:

CALL FORWARD
CALL DELAY_QS
JUMP LOOP

;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ileri ve geri fonksiyonlari birlestirilebilir 
ilk bitin degeri main icinde verilirse

    FORWARD:                    ; her hamleden once pwm 0 ediliyor
    LOAD sE, 00         
    OUTPUT sE, MOTOR_R      ; MOTOR_R gelen port id'e gore degisecek
    OUTPUT sE, MOTOR_L      ; ikinci pwm modulune
    TEST sE, 00         ; delay

    ADD sE, SPEED
    ADD sE, 80          ; simdiki sisteme gore ilk biti 1 yapilip ileri yon 
veriliyor

    OUTPUT sE, MOTOR_R      
    OUTPUT sE, MOTOR_L

    LOAD sE, 00
    RETURN


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
RIGHT:
    LOAD sE, 00
    OUTPUT sE, MOTOR_R
    OUTPUT sE, MOTOR_L
    TEST sE, 00

    ADD sE, SPEED
    ADD sE, 80          ; bu herhalde ileri olacak :D

    OUTPUT sE, MOTOR_R      ; sag motor MOTOR_R deymis gibi

    LOAD sE, 00
    RETURN

LEFT:
    LOAD sE, 00
    OUTPUT sE, MOTOR_R
    OUTPUT sE, MOTOR_L
    TEST sE, 00

    ADD sE, SPEED
    ADD sE, 80          ; bu herhalde ileri olacak :D

    OUTPUT sE, MOTOR_L      ; sol motor MOTOR_L deymis gibi

    LOAD sE, 00
    RETURN
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;      
FORW_R:
    LOAD sE, 00
    OUTPUT sE, MOTOR_R
    OUTPUT sE, MOTOR_L
    TEST sE, 00

    ADD sE, SPEED
    SR0 sE              ; sol motora hizin yarisi gitsin
    ADD sE, 80          ; ikisi de ileri

    OUTPUT sE, MOTOR_L
    TEST sE, 00         ; delay

    ADD sE, SPEED           ; sag motora hizin bir bucuk kati gitsin

    OUTPUT sE, MOTOR_R

    LOAD sE,00
    RETURN


FORW_L:
    LOAD sE, 00
    OUTPUT sE, MOTOR_R
    OUTPUT sE, MOTOR_L
    TEST sE, 00

    ADD sE, SPEED
    SR0 sE              ; sag motora hizin yarisi gitsin
    ADD sE, 80

    OUTPUT sE, MOTOR_R
    TEST sE, 00         ; delay

    ADD sE, SPEED           ; sol motora hizin bir bucuk kati gitsin

    OUTPUT sE, MOTOR_L

    LOAD sE,00
    RETURN
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
DELAY_1S:
    LOAD s0, 80
    LOAD s1, F0
    LOAD s2, FA
    LOAD s3, 02

DONGU1:
    SUB s0, 01
    JUMP NZ, DONGU1
DONGU2:
    SUB s1, 01
    JUMP Z, DONGU3
    LOAD s0, FF
    JUMP DONGU1
DONGU3:
    SUB s2, 01
    JUMP Z, DONGU4
    LOAD s1, FF
    JUMP DONGU2
DONGU4:
    SUB s3, 01
    RETURN Z
    LOAD s2, FF
    JUMP DONGU3

    RETURN          ; bu komut calisirsa fonksiyon yanlistir :D



ISR:
INPUT sC, REMOTE    ; bluetoothtan veri okunsun

COMPARE sC, ILERI       ; komutlari tek tek deniyo, ilerde TEST kullanan 
 guzel bu hale getirebilirim
JUMP NZ, SECIM2
CALL FORWARD        ; bu 1 saniyelik ileri komutu
CALL DELAY_1S
RETURNI ENABLE

SECIM2:
COMPARE sC, SAG
JUMP NZ, SECIM3
CALL RIGHT          ; 1 saniyelik sag
CALL DELAY_1S
RETURNI ENABLE

SECIM3:
COMPARE sC, SOL
JUMP NZ, SECIM4
CALL LEFT           ; 1 saniyelik sol
CALL DELAY_1S
RETURNI ENABLE

SECIM4:
COMPARE sC, SAGX
JUMP NZ, SECIM5
CALL FORW_R         ; 1 saniyelik ileri sag
CALL DELAY_1S
RETURNI ENABLE

SECIM5:
COMPARE sC, SOLX
JUMP NZ, SECIM6
CALL FORW_L         ; 1 saniyelik ileri sol
CALL DELAY_1S
RETURNI ENABLE

SECIM6:
COMPARE sC, ILERI2
JUMP NZ, SECIM7
CALL FORWARD        ; 3 saniyelik ileri
CALL DELAY_1S
CALL DELAY_1S
CALL DELAY_1S
RETURNI ENABLE

SECIM7:
COMPARE sC, SAG2
JUMP NZ, SECIM8
CALL RIGHT          ; 3 saniyelik sag
CALL DELAY_1S
CALL DELAY_1S
CALL DELAY_1S
RETURNI ENABLE

SECIM8:
COMPARE sC, SOL2
JUMP NZ, SECIM9
CALL LEFT           ; 3 saniyelik sol
CALL DELAY_1S
CALL DELAY_1S
CALL DELAY_1S
RETURNI ENABLE  

SECIM9:
COMPARE sC, SAGX2
JUMP NZ, SECIM10
CALL FORW_R         ; 3 saniyelik ileri sag
CALL DELAY_1S
CALL DELAY_1S
CALL DELAY_1S
RETURNI ENABLE

SECIM10:
COMPARE sC, SOLX2
JUMP NZ, SECIM11
CALL FORW_L         ; 3 saniyelik ileri SOL
CALL DELAY_1S
CALL DELAY_1S
CALL DELAY_1S
RETURNI ENABLE

SECIM11:
COMPARE sC, HIZLAN
JUMP NZ, SECIM12

COMPARE SPEED, 78       ; hiz zaten max ise atla
JUMP C, GECERSIZ
ADD SPEED, 20       ; degilse 20 eklesin (hexa)
RETURNI ENABLE

SECIM12:
COMPARE sC, YAVASLA
JUMP NZ, GECERSIZ

COMPARE SPEED, 20       ; hiz zaten min ise atla
JUMP C, GECERSIZ
SUB SPEED, 20       ; degilse 20 azalt
RETURNI ENABLE

GECERSIZ:
RETURNI ENABLE      ; komut bos ise direk cik


ADDRESS 3FF
JUMP ISR

субмодуль был взят из github.наш код Bluetooth Verilog:

module uart(
     input wire [7:0] din,
    input wire wr_en,
    input wire clk_50m,
    output wire tx,
    output wire tx_busy,
    input wire rx,
    output wire rdy,
    input wire rdy_clr,
    output reg [7:0] dout,
     output tx_, 

   // input wire select,
     output reg interrupt,
     input interrupt_ack
     );


wire [7:0] rx_dout;
//reg [7:0] dout;

baud_rate_gen uart_baud(
        .clk_50m(clk_50m),
        .rxclk_en(rxclk_en),
        .txclk_en(txclk_en)
        );

 transmitter uart_tx(
        .din(din),
       .wr_en(wr_en),
       .clk_50m(clk_50m),
       .clken(txclk_en),
        .tx(tx),
       .tx_busy(tx_busy)
        );

  receiver uart_rx(
        .rx(rx),
        .rdy(rdy),
        .rdy_clr(rdy_clr),
        .clk_50m(clk_50m),
        .clken(rxclk_en),
        .data(rx_dout)
        );

     assign tx_ = 1;

initial
begin
interrupt = 1'b0;
end

always @ (posedge clk_50m)
begin
if(dout != rx_dout)
begin
dout <= rx_dout;

case(dout)
8'b00000000 : interrupt = 1;
8'b00000001 : interrupt = 1;
8'b00000010 : interrupt = 1;
8'b00000011 : interrupt = 1;
8'b00000100 : interrupt = 1;
8'b00000101 : interrupt = 1;
8'b00000110 : interrupt = 1;
//8'b000000111 :
8'b00001000 : interrupt = 1;
8'b00001001 : interrupt = 1;
8'b00001010 : interrupt = 1;
8'b00001011 : interrupt = 1;
8'b00001100 : interrupt = 1;
default: interrupt = 0;

endcase
end

if(interrupt_ack)
    interrupt = 0;


end





 endmodule
...