Thông báo

Collapse
No announcement yet.

Mức ưu tiên ngắt trong Atmega16

Collapse
X
 
  • Lọc
  • Giờ
  • Show
Clear All
new posts

  • #16
    Nguyên văn bởi TP_Electro Xem bài viết
    Mình thiếu bổ sung thêm là sau khi thực hiện xong cái ngắt sau(cấp 2) nó quay về lại cái ngắt trước (cấp 1). Thanks bác.
    Ok, cảm ơn bác, mình hiểu rồi nó khác 8051 là khi vào ngắt nó tự động clear bit (i)ngắt toàn cục để các disable tất cả các ngắt. Nếu mà vừa nhảy đến ngắt cấp 1 mình set bit i luôn thì ngắt cấp 2 có thể chạy được và khi nhảy đến ngắt cấp 2 nó lại clear i nên khi nó thục thi xong ngắt cấp 2 nó quay lại ngắt cấp 1 và thực thi cho đến hêt ngắt cấp 1 rồi thoát. Phải ko bác nhỉ? Mình gì đang học c cho AVR có dùng ngắt timer và ADC nhưng sơ ngắt ADC nó ảnh hưởng đến pwm. Giờ biết thì ko lo nữa rồi.
    Bác thật nhanh nhạy. Lý thuyết thì đúng là như vậy. Hi vọng bác sẽ làm đc.
    Có 2 điều cần lưu ý khi sử dụng nested interrupt là:
    - Tốn nhiều bộ nhớ
    - Dễ rơi vào vòng lặp mãi mãi (recursion) -> uC tràn stack -> tự reset
    Chúc bác thành công.

    Comment


    • #17
      Nguyên văn bởi developerv Xem bài viết

      cái này thì bạn khỏi lo trong adc bạn cứ phục vụ adc còn pwm nó cứ chạy pwm. cái nào thực hiện trước đều được mà .
      Mình lo PCU đang vừa vào phục vụ cho ngắt ADC mà trúng lúc thằng PWM cũng yêu cầu phục vụ nó nữa mà bỏ lở có mà sai bét duty thì khổ. Mà chắc là trường hợp này có xảy ra nếu 2 ngắt đều active.

      Comment


      • #18
        Nguyên văn bởi TP_Electro Xem bài viết
        Mình lo PCU đang vừa vào phục vụ cho ngắt ADC mà trúng lúc thằng PWM cũng yêu cầu phục vụ nó nữa mà bỏ lở có mà sai bét duty thì khổ. Mà chắc là trường hợp này có xảy ra nếu 2 ngắt đều active.
        K đến mức vậy đâu.khi đang thực hiện ngắt này mà có ngắt khác thì cờ ngắt nó vẫn dc set.sau khi thực hiện xong rồi thì nó thực hiện ngắt kế tiếp.nên k lo bị bỏ lỡ ngắt

        Comment


        • #19
          Nguyên văn bởi developerv Xem bài viết

          K đến mức vậy đâu.khi đang thực hiện ngắt này mà có ngắt khác thì cờ ngắt nó vẫn dc set.sau khi thực hiện xong rồi thì nó thực hiện ngắt kế tiếp.nên k lo bị bỏ lỡ ngắt
          Theo file application note của bác nvt2 gởi thì mình thấy khi vào ngắt là bit cho phép ngắt toàn cục bị disable, còn cờ ngắt thì ko thấy đề cập, nhưng chắc là nó đc clear khi thoát ngắt nó. Còn bạn nói đợi cho nó thực hiện ngắt cấp 1 xong rồi mới đến ngắt cấp 2( ngắt quan trọng nhất) trong trường hợp mà trình isr của ngắt cấp 1 dài chiếm nhiều time thì việc xử lí ở ngắt cấp 2 bị chậm rồi. Cho nên mình muốn ngoài mức ưu tiên ngắt cao hơn, ngắt cấp 2 phải đc ưu tiên trong cả khi PC đã vào các ngắt khác nữa thì mới đảm bảo cho việc xử lí trong ngắt cấp 2 ko bị chậm.

          Comment


          • #20
            Nguyên văn bởi htc2k14 Xem bài viết

            Bác thật nhanh nhạy. Lý thuyết thì đúng là như vậy. Hi vọng bác sẽ làm đc.
            Có 2 điều cần lưu ý khi sử dụng nested interrupt là:
            - Tốn nhiều bộ nhớ
            - Dễ rơi vào vòng lặp mãi mãi (recursion) -> uC tràn stack -> tự reset
            Chúc bác thành công.
            Ok. Thanks sự góp ý quan trọng của bác.

            Comment


            • #21
              Nguyên văn bởi TP_Electro Xem bài viết

              Ok. Thanks sự góp ý quan trọng của bác.
              để chắc chắn bạn có thể test kiểu này. trong ngắt ADC bạn để delay khoảng nào đó. thời gian delay này lớn hơn thời gian pwm rồi bạn soi chân ra pwm xem nó có đều k. nếu nó vẫn chạy ổn định thì có nghĩa là k bị ảnh hưởng. hoặc cũng có thể dùng 2 ngắt timer để test. có thể đảo 2 cái cho nhau xem cái nào dc ưu tiên hơn.

              Comment


              • #22
                Các bác cho hỏi thêm về đoạn code đổi sang digit để hiển thị như đoạn bên dưới mình cho biến so = 100, vậy chổ dòng chuyển đổi tram =(so%1000)/100; làm sao để trăm = 1 được. Mình tính thì nó =0. Theo đó phép chia % trong ngoặc được 1 sau đó 1 chia / cho 100 thì lấy phần nguyên lại được có 0. Thế mà sao hàm chạy vẫn hiển thị ra được 100 nhỉ?.
                nghin=so/1000;
                tram=(so%1000)/100;
                chuc=(so%100)/10;
                dv=so%10;

                Mình dùng đoạn code dưới thì thấy cũng đúng nhưng cách tính hàng trăm thì hơi khác. nó ra được 1 còn ở trên thì 0.
                dv=so%10;
                chuc=(so/10)%10;
                tramso/10)/10)%10;
                nghin(so/10)/10)/10)%10;

                Comment


                • #23
                  Nguyên văn bởi TP_Electro Xem bài viết
                  Các bác cho hỏi thêm về đoạn code đổi sang digit để hiển thị như đoạn bên dưới mình cho biến so = 100, vậy chổ dòng chuyển đổi tram =(so%1000)/100; làm sao để trăm = 1 được. Mình tính thì nó =0. Theo đó phép chia % trong ngoặc được 1 sau đó 1 chia / cho 100 thì lấy phần nguyên lại được có 0. Thế mà sao hàm chạy vẫn hiển thị ra được 100 nhỉ?.
                  nghin=so/1000;
                  tram=(so%1000)/100;
                  chuc=(so%100)/10;
                  dv=so%10;

                  Mình dùng đoạn code dưới thì thấy cũng đúng nhưng cách tính hàng trăm thì hơi khác. nó ra được 1 còn ở trên thì 0.
                  dv=so%10;
                  chuc=(so/10)%10;
                  tramso/10)/10)%10;
                  nghin(so/10)/10)/10)%10;
                  Khả năng là trình biên dịch có bug. Không thấy phép chia trong bộ ALU của ATmel16. Cho nên việc tính toán sẽ dựa trên trình biên dịch.

                  Comment


                  • #24
                    Nguyên văn bởi htc2k14 Xem bài viết

                    Khả năng là trình biên dịch có bug. Không thấy phép chia trong bộ ALU của ATmel16. Cho nên việc tính toán sẽ dựa trên trình biên dịch.
                    Mình nghĩ là nó tính toán bằng khối lệnh của ALU do cấu trúc c tạo ra chứ ko phải trình biên dịch. Vì trình biên dịch chỉ tính được các hằng chứ biến làm sao nó tính. vì nó chưa biến trong biến là gì. Khi nó dịch thì chương trình chưa chạy mà bác.

                    Comment


                    • #25
                      Nguyên văn bởi TP_Electro Xem bài viết

                      Mình nghĩ là nó tính toán bằng khối lệnh của ALU do cấu trúc c tạo ra chứ ko phải trình biên dịch. Vì trình biên dịch chỉ tính được các hằng chứ biến làm sao nó tính. vì nó chưa biến trong biến là gì. Khi nó dịch thì chương trình chưa chạy mà bác.
                      1. Đúng là tính toán sẽ được thực hiện bởi ALU.
                      2. Mình chưa hiểu ý của bác, mong bác nói thêm
                      Câu sau chưa đúng lắm vì 1 và trình biên dịch ko thực thi việc tính toán.

                      Comment


                      • #26
                        Nguyên văn bởi htc2k14 Xem bài viết

                        1. Đúng là tính toán sẽ được thực hiện bởi ALU.
                        2. Mình chưa hiểu ý của bác, mong bác nói thêm
                        Câu sau chưa đúng lắm vì 1 và trình biên dịch ko thực thi việc tính toán.
                        Ý mình là trình biên dịch nó có sẵn các khối lệnh thực hiện phép tính được viết bằng các lệnh đơn. Mình ko nói trình biên dịch nó tính toán đâu. Mình nói thế vì thấy bác nói " Cho nên việc tính toán sẽ dựa trên trình biên dịch. ". có thể mình hiểu nhầm ý bác nên viết thế.

                        Ah, bác chỉ cách mình cách copy một chuổi dữ liệu vào ram với. Ví dụ như mình nhận được ở uart liên tục 6 byte. asm cho 8051 thi mình biết chứ C chưa biết chổ này. Và thêm cách capture nó hoạt động sao nhỉ .thanks.

                        Comment


                        • #27
                          Nguyên văn bởi TP_Electro Xem bài viết
                          Ý mình là trình biên dịch nó có sẵn các khối lệnh thực hiện phép tính được viết bằng các lệnh đơn. Mình ko nói trình biên dịch nó tính toán đâu. Mình nói thế vì thấy bác nói " Cho nên việc tính toán sẽ dựa trên trình biên dịch. ". có thể mình hiểu nhầm ý bác nên viết thế.

                          Ah, bác chỉ cách mình cách copy một chuổi dữ liệu vào ram với. Ví dụ như mình nhận được ở uart liên tục 6 byte. asm cho 8051 thi mình biết chứ C chưa biết chổ này. Và thêm cách capture nó hoạt động sao nhỉ .thanks.
                          Trình biên dịch có bug nghĩa là 100%1000 thì ko thực hiện đc trong khi 100%10 lại thực hiện đc, cả 2 đều là phép modulo cả. (phỏng đoán là trình biên dịch ko hỗ trợ floating point.)

                          Ko hiểu lắm, khi bác dùng 1 biến tạm để lưu uart thì khi đọc nó đã lưu vào RAM rồi? Ý bác là lưu vào 1 vùng nhớ cụ thể trên RAM hay thế nào? Muốn lưu 6 bytes thì tạo 1 chuỗi (6 bytes hay nhiều hơn) và lưu là đc mà. UART nó vào thanh ghi FIFO, đọc hay gán nó vào 1 biến thì thanh ghi FIFO sẽ tự xóa, mặc định phần cứng là như thế.

                          Comment


                          • #28
                            Mình ngẩm mấy ngày rồi mà ko nghĩ ra 2 đoạn code này cho ra kết quả cũng là % của "dutyspwm_tho" theo biến "phan_tram_level" . Dưới 90% thì ok, mà >90% là hàm 1 ko ra đúng. Dù chính mình viết ra 2 đoạn (do hàm 1 chỉ chạy được ra được 0 - 90% nên minh viết tiếp hàm 2 lại chạy được 0 - 100%. Nhưng mình hông hiểu đc trình dịch lỗi hay proteus lỗi. Hàm chuyển đổi 1 không ra đúng khi "phan_tram_level" >90. kết quả lưu vào biến "temp". Mong các bác chỉ thêm cho.
                            Hàm 1:
                            unsigned int dutyspwm_tho ;
                            unsigned int temp,n,m ;
                            temp= (dutyspwm_tho*phan_tram_level)/100 ;

                            Hàm 2:
                            unsigned int dutyspwm_tho ;
                            unsigned int temp,n,m ;



                            if (phan_tram_level>90){ //chi lay max 90% truoc.
                            temp= (dutyspwm_tho*90)/100 ; //Sau do lay so % le tu 1 den 10 cua 10% con lai,
                            // roi sau do cong lai de co so % > 90%. Viec tinh vong vo
                            // la can thiet vi de tranh loi xung pwm ra khi tren 90% khi mo phong.
                            switch (phan_tram_level) {

                            case 91: n = 1;
                            break;
                            case 92: n = 2;
                            break;
                            case 93: n = 3;
                            break;
                            case 94: n = 4;
                            break;
                            case 95: n = 5;
                            break;
                            case 96: n = 6;
                            break;
                            case 97: n = 7;
                            break;
                            case 98: n = 8;
                            break;
                            case 99: n = 9;
                            break;
                            case 100: n =10;
                            break;
                            default:
                            };

                            m = (dutyspwm_tho*n)/100 ; //tinh phan tram le
                            temp = temp + m; //cong lai de co tren 90%
                            }
                            else {
                            temp= (dutyspwm_tho*phan_tram_level)/100 ;
                            };

                            Comment

                            Về tác giả

                            Collapse

                            postmanbk Tìm hiểu thêm về postmanbk

                            Bài viết mới nhất

                            Collapse

                            Đang tải...
                            X