2011-10-26 33 views
6

Tôi có một số phần cứng mà tôi muốn mô phỏng; tôi tự hỏi nếu tôi có thể làm điều đó ở mức thấp như thế này. Các phần cứng có nhiều thanh ghi, mà tôi sắp xếp trong một cấu trúc:Cách mô phỏng ánh xạ bộ nhớ I/O

#include <stdint.h> 
struct MyControlStruct 
{ 
    uint32_t data_reg_1; 
    uint32_t data_reg_2; 
    uint32_t dummy[2]; // to make the following registers have certain addresses 
    uint32_t control_reg_1; 
    uint32_t control_reg_2; 
}; 
volatile struct MyControlStruct* MyDevice = (struct MyControlStruct*)0xDeadF00; 

Vì vậy, tôi muốn hỗ trợ cú pháp sau để truy cập phần cứng trên Windows và Linux:

MyDevice->data_reg_1 = 42; 
MyDevice->data_reg_2 = 100; 
MyDevice->control_reg_1 = 1; 

Khi dòng cuối cùng của mã được thực thi, tôi muốn trình mô phỏng phần cứng "đánh thức" và thực hiện một số công cụ. Tôi có thể thực hiện điều này trên Windows và/hoặc Linux không? Tôi nghĩ về việc bằng cách nào đó bắt tín hiệu "lỗi phân đoạn", nhưng không chắc chắn liệu điều này có thể được thực hiện trên Windows hay không.

Tôi đã xem trang hướng dẫn sử dụng mmap; nó có vẻ như nó có thể giúp đỡ, nhưng tôi không thể hiểu làm thế nào tôi có thể sử dụng nó. Tất nhiên, tôi có thể trừu tượng truy cập vào phần cứng bằng cách xác định các chức năng như WriteToMyDevice, và mọi thứ sẽ dễ dàng (có thể), nhưng tôi muốn hiểu liệu tôi có thể sắp xếp truy cập vào phần cứng của mình theo cách chính xác này hay không. Không phải là một cách dễ dàng.

+0

"Mức thấp" của bạn quá cao ... Cả trong Windows và trong phần cứng Linux truy cập được thực hiện từ chế độ hạt nhân. Bạn cần suy nghĩ về nhiều chi tiết triển khai hơn - cách nói chuyện với phần cứng. Ví dụ, bạn có thể viết trình điều khiển thực và trình mô phỏng trình điều khiển. –

+0

Vì vậy, việc sử dụng các địa chỉ bộ nhớ được xác định trước trong chế độ người dùng là không thể? – anatolyg

+0

Bạn không thể nói chuyện trực tiếp với thiết bị phần cứng từ chế độ người dùng Windows/Linux bằng quyền truy cập bộ nhớ trực tiếp. Điều này chỉ có thể ở chế độ hạt nhân. Đây là lý do tại sao tôi đề nghị bạn suy nghĩ đầu tiên về chi tiết triển khai. Nếu không có chúng, bạn thực sự không biết phải cạnh tranh gì. –

Trả lời

2

Về nguyên tắc, bạn có thể mã (unportably) một trình xử lý cho SIGSEGV sẽ bẫy và xử lý quyền truy cập vào các trang không mong muốn và có thể kiểm tra xem địa chỉ được chỉ định có được truy cập hay không.

Để thực hiện điều đó trong Linux, bạn cần phải sử dụng cuộc gọi hệ thống sigaction với SA_SIGINFO và sử dụng đối số thứ ba của trình xử lý tín hiệu của mình.

Điều này cực kỳ không thể chuyển đổi: bạn sẽ phải viết mã khác nhau cho các Unix khác nhau (có lẽ ngay cả số phiên bản hạt nhân Linux của bạn có thể quan trọng) và khi thay đổi bộ vi xử lý.

Và tôi đã nghe nói rằng hạt nhân Linux không nhanh chóng xử lý như vậy.

Các hạt nhân tốt hơn khác (Hurd, Plan9) cung cấp phân trang cấp người dùng, điều này sẽ giúp ích.

1

Trong thực tế giả lập của bạn (khá thô lỗ) có thể trên linux với mã không gian người dùng thuần túy.

Xây dựng giả lập, chỉ cần có một sợi giây hoặc quá trình (sử dụng bộ nhớ chia sẻ, hoặc có lẽ một file mmap'd và inotify) xem bộ nhớ mà được bắt chước bộ nhớ ánh xạ thiết bị

Đối với người lái xe phần cứng thực , bạn sẽ cần một chút mã hạt nhân, nhưng điều đó có thể chỉ đơn giản là cái gì đó ánh xạ địa chỉ phần cứng thực tế vào không gian người dùng với các quyền thích hợp. Thực tế điều này làm cho một môi trường hoạt động đa người dùng hiện đại hoạt động như một hộp dos cũ hoặc một bộ điều khiển vi mô đơn giản - không phải là thực hành tuyệt vời, nhưng khả thi ít nhất là nơi an ninh không phải là mối quan tâm.

Một điều khác bạn có thể xem xét sẽ chạy mã trong máy ảo.

Nếu mã bạn sẽ thực hiện là của riêng bạn, có thể tốt hơn để viết nó theo cách di động để bắt đầu, trừu tượng truy cập phần cứng thành các chức năng mà bạn có thể viết lại cho mỗi nền tảng (ví dụ: OS, phiên bản phần cứng hoặc vật lý/mô phỏng). Các kỹ thuật này hữu ích hơn nếu đó là mã hiện có của người khác mà bạn cần để tạo môi trường. Một điều bạn có thể xem xét (nếu bản gốc không được tích hợp quá chặt chẽ) đang sử dụng chức năng đánh chặn mức thư viện động của các chức năng cụ thể, ví dụ với LD_PRELOAD trên Linux hoặc dll trình bao trên cửa sổ. Hoặc cho rằng vấn đề, vá nhị phân.

1

Ban đầu tôi hiểu nhầm câu hỏi của bạn. Bạn có một phần của bộ nhớ ánh xạ phần cứng và bạn muốn thi đua của bạn được tương thích nhị phân. Trên Windows, bạn có thể cấp phát bộ nhớ cho cấu trúc bằng VirtualAlloc và biến nó thành trang bảo vệ và bắt mọi truy cập vào nó bằng SEH.

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