2010-05-18 25 views
5

Cho rằng, trên ARM Cortex M3, tôi có thể:ARM cortex: mutex sử dụng chút dải

  • nguyên tử đọc một chút đơn
  • nguyên tử thiết kế hơi đơn
  • nguyên tử rõ ràng một chút đơn

Làm thế nào tôi có thể kết hợp những cho một phong cách thiết mutex hoạt động:

try lock 
take lock 
release lock 

Có vẻ như try_lock hoặc take_lock sẽ yêu cầu hai hoạt động không phải là nguyên tử.

Tôi có cần kiểm soát nhiều hơn để thực hiện việc này không? Vô hiệu hóa ngắt toàn cầu sẽ làm điều đó nhưng có vẻ như cần phải có một cách tiếp cận phẫu thuật hơn.

Trả lời

4

rwl_TryLock() của bạn không nhất thiết phải trả lại lỗi nếu khóa đã được giữ khi nó được gọi (trình biên dịch của bạn nên đưa ra ít nhất một cảnh báo về mã đường dẫn không có giá trị trả lại). Hãy thử như sau:.

int rwl_TryLock(volatile uint32_t *lock, int who){ 

    Var_SetBit_BB((uint32_t)lock, who); 
    if(*lock == (1<<who)){ // check that we have exclusive access 
     // got the lock! 
     return 1; 
    } 

    // do not have the lock 
    Var_ResetBit_BB((uint32_t)lock, who); // clear the lock flag 
    return 0; 
} 

Lưu ý rằng ở trên sẽ không làm việc cho đệ quy tuyên bố khóa tương tự (ví dụ, nếu nhiệm vụ theo quy định của who == 1 đã có khóa và cố gắng để xác nhận lại danh, các mã trên sẽ không hoạt động chính xác), nhưng điều đó cũng đúng với bản gốc của bạn.

Ngoài ra, ngắt có thể bị tắt/bật trên Cortex M3 khá nhanh (đây là bản cập nhật đơn giản cho thanh ghi NVIC). Bạn có chắc chắn rằng hệ thống của bạn không thể sống với một vài chu kỳ gián đoạn gián đoạn bổ sung để giữ mã để xử lý cấu trúc dữ liệu khóa đơn giản (thường có nghĩa là dễ dàng hơn để thực hiện chính xác)?

1

Một số để biết sau khi một số tìm kiếm:.

" ARM Cortex-M3-bit dải lõi vi điều khiển ARM cung cấp một cách khác để thực hiện Cột Viết tiếp cận với các biến trong khu vực chút băng tần bí danh gây một nguyên tử đọc-sửa đổi – ghi quyền truy cập vào vị trí bộ nhớ trong vùng dải bit ở mức bus hệ thống Biến đổi trong vùng bit-band có thể dùng làm vùng chứa cho các semaphores. Bất cứ khi nào một khách hàng cần phải yêu cầu semaphore, nó đặt bit của riêng nó bằng cách viết 1 đến vị trí tương ứng trong vùng bí danh dải bit. d kiểm tra xem không có bit nào khác được đặt, nghĩa là khách hàng đã xác nhận thành công semaphore. Trong trường hợp các bit khác được thiết lập, client sẽ phải xóa bit của chính nó một lần nữa, và thử lại (có lẽ sau khi chờ đợi). " (source)

Đây là thô của tôi (chưa được kiểm tra) giải thích:

/* 
* Frees a lock. 
* 
* @note lock must point to a fully aligned 32 bit integer. 
* (atomically set to 0) 
* 
* @returns 1 if successfull 
*/ 
int rwl_FreeLock(volatile uint32_t *lock){ 
    *lock = 0; 
    return 1; // always successful 
} 

/* 
* Attempts to acquire a lock 
* @param who is the client taking the lock 
* @lock pointer to the mutex (uint32_t value in memory) 
* @note lock must point to a fully aligned 32 bit integer. 
* (atomically set to 1 only if set to 0) 
*/ 
int rwl_TryLock(volatile uint32_t *lock, int who){ 
    // initial check of lock 
    if(*lock == 0){ 
     Var_SetBit_BB((uint32_t)lock, who); 
     if(*lock == (1<<who)){ // check that we still have exclusive access 
      // got the lock! 
      return 1; 
     } else { 
        // do not have the lock 
      Var_ResetBit_BB((uint32_t)lock, who); // clear the lock flag 
      return 0; 
     } 
    } 
} 

Var_Set_BB/Var_Reset_BB:. Thiết lập/rõ ràng một chút chút bằng dải (nguyên tử)

Tuy nhiên, nó không không hoạt động !!!

+0

Nếu hai điều cố gắng truy cập vào khóa, nó sẽ có vẻ như cả hai truy cập có thể báo cáo thất bại . Một cách tiếp cận tốt hơn là sử dụng spinloop ldrex/strex. Điều đó đã được nói, ở mức độ nào mà các truy cập bit-band đảm bảo nguyên tử trong sự hiện diện của những thứ như DMA và như vậy? Nếu việc ghi DMA và ghi băng bit xảy ra gần như đồng thời, thì ghi DMA có đảm bảo không xảy ra giữa các khía cạnh 'đọc' và 'ghi' của bit-band viết không? – supercat

0

Tôi chưa từng sử dụng bit-banding trên ARM; nghiêng của tôi thay vì sẽ sử dụng tải độc quyền/lưu trữ-có điều kiện cho tất cả các hoạt động đó. Sử dụng vòng lặp để tải độc quyền giá trị cũ, tính giá trị mới và sử dụng cửa hàng có điều kiện để ghi lại.Lặp lại cho đến khi cửa hàng có điều kiện thành công (có thể đây sẽ là lần thứ hai, nếu nó không phải là lần đầu tiên).

2

Dải bit sẽ không hoạt động trong trường hợp này. Nó chỉ là một cách thực sự gọn gàng của các bit thiết lập trong các tập tin đăng ký thiết bị và bộ nhớ của bạn. Sử dụng các hướng dẫn tải độc quyền và lưu trữ độc quyền để triển khai semaphore/mutex của bạn. Dưới đây là một tài liệu ví dụ bạn có thể sử dụng để thực hiện một semaphore bằng cách sử dụng các hướng dẫn này và nó chi tiết cách thức hoạt động của nó.

http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.ddi0439b/CHDDIGAC.html

đó đang được nói, bạn có thể giảm bộ nhớ của mutexes của bạn bằng cách sử dụng chút dải ...

Các vấn đề liên quan