2012-01-11 33 views
6

Tôi cần phải trải qua một tệp C/C++ và trích xuất danh sách các lớp và phương thức và vị trí của chúng trên tệp.Cách phân tích/phân tích đơn giản mã C/C++ từ C# để lấy danh sách các phương thức

libclang là tùy chọn tốt nhất? Hay là "quá nhiều" cho công việc?

Sẽ tốt hơn nếu chỉ tìm kiếm các cặp ngoặc vuông?

Trong trường hợp libclang là lựa chọn: có cách nào để gọi nó từ C# không?

Cảm ơn!

+0

Tất nhiên luôn có cách gọi mã C++ từ .NET, sử dụng C++/CLI. Một giải pháp di động hơn sẽ là cung cấp một wrapper C đồng bằng xung quanh libclang (nên khá đơn giản). Nhưng giải pháp tốt nhất có thể là để đi cho một phiên bản cũ của Clang, trở lại khi máy in XML đẹp của nó vẫn còn tồn tại. Thật là buồn vì nó đã bị loại khỏi Clang. –

+0

Một tùy chọn khác (một chút gỉ, nhưng vẫn hoạt động đối với hầu hết các trường hợp) là trình phân tích cú pháp của Elsa kết hợp với bộ tiền xử lý gcc. –

+0

Bạn không rõ ràng về cách chính xác câu trả lời bạn muốn. Bạn có thể xây dựng một giải pháp dựa trên các cặp ngoặc đơn có khả năng tạo ra thông tin về phương thức/lớp đơn giản 90% thời gian, với các lỗi ngoạn mục 10% khác. Bạn định làm gì với kết quả? –

Trả lời

6

Bạn có thể xem xét ctags, có sẵn trên nhiều nền tảng. Đầu ra có thể dễ dàng phân tích cú pháp và đầy đủ thông tin bạn yêu cầu.

thông tin khác Đối với câu hỏi của bạn, tôi phải xem xét nhiều tùy chọn có sẵn và sau một ít tôi tìm thấy nó. Ví dụ:

ctags -N -x --c-kinds=+p crowd.* 

sản xuất sản lượng này

CrowdSim   class  44 crowd.h   class CrowdSim 
CrowdSim   function  47 crowd.h   CrowdSim(const std::string& contentDir) : _contentDir(contentDir) {} 
Particle   function  35 crowd.h   Particle() 
Particle   struct  25 crowd.h   struct Particle 
_contentDir  member  56 crowd.h   std::string _contentDir; 
_crowd_H_  macro  18 crowd.h   #define _crowd_H_ 
_particles  member  57 crowd.h   std::vector<Particle> _particles; 
animTime   member  32 crowd.h   float animTime; 
chooseDestination function  24 crowd.cpp  void CrowdSim::chooseDestination(Particle &p) 
chooseDestination prototype 53 crowd.h   void chooseDestination(Particle &p); 
dx    member  28 crowd.h   float dx, dz; // Destination position 
dz    member  28 crowd.h   float dx, dz; // Destination position 
fx    member  29 crowd.h   float fx, fz; // Force on particle 
fz    member  29 crowd.h   float fx, fz; // Force on particle 
init    function  35 crowd.cpp  void CrowdSim::init() 
init    prototype 49 crowd.h   void init(); 
node    member  31 crowd.h   H3DNode node; 
ox    member  30 crowd.h   float ox, oz; // Orientation vector 
oz    member  30 crowd.h   float ox, oz; // Orientation vector 
px    member  27 crowd.h   float px, pz; // Current postition 
pz    member  27 crowd.h   float px, pz; // Current postition 
update   function  68 crowd.cpp  void CrowdSim::update(float fps) 
update   prototype 50 crowd.h   void update(float fps); 

(lưu ý: -x chỉ là để kiểm tra người sử dụng dễ dàng)

+0

Có vẻ như đây có lẽ là lựa chọn tốt nhất. Nó có thể cho bạn biết một phương pháp VÀ cơ thể của nó ở đâu không? Hoặc chỉ nơi khai báo phương thức là? Ví dụ: – pablo

+0

, đối với chức năng CrowdSim :: update, có thể biết cơ thể của nó ở đâu không? – pablo

+0

vâng, cơ thể nằm ở dòng crow.cpp 68 – CapelliC

0

Tốt hơn nên sử dụng trình phân tích cú pháp đầy đủ IMO. Bạn có thể sử dụng ANTLR. Nó có cả ngữ pháp C/C++ và trình tạo trình phân tích cú pháp C#.

+1

Ngữ pháp ANTLR cho C/C++ không tốt bằng libclang AFAIK. libclang thực hiện công việc cho bạn, bạn đã trang trí toàn bộ ngữ pháp C/C++ nếu bạn muốn đi theo cách ANTLR – pablo

+1

Một "trình phân tích cú pháp đầy đủ" không đủ gần, khi có một bộ tiền xử lý và một đường dẫn bao gồm các nền tảng phức tạp cấu hình hiện tại. –

+1

... và tôi không nghĩ ngữ pháp ANTLR thực sự đã hoàn thành. Ghi chú phát hành chứa thông tin tác giả cho biết anh ta không thực sự hoàn thành nó. –

1

Không chắc chắn tùy chọn nào là tốt nhất, nhưng bạn cũng có thể xem GCC-XML hoặc Mono/CXXI. Cái thứ hai sử dụng GCC-XML trong nội bộ, nhưng cũng cung cấp các giao diện C# cho các định nghĩa lớp C++.

libclang là thư viện C và do đó có thể sử dụng được từ .NET thông qua P/Invoke, nhưng có thể khá tẻ nhạt khi lặp lại tất cả các khai báo cần thiết trong C#.

1

Một góc khác là tạo tiện ích mở rộng cho Visual Studio.

+0

Nó chắc chắn là một lựa chọn, đặc biệt với các công cụ mới trên phiên bản mới nhất, nhưng tôi muốn có một giải pháp VS độc lập. – pablo

+0

ah, ok. tốt, tôi sẽ để nó vào, trong trường hợp ai đó thấy nó hữu ích cho nhu cầu của họ. – justin

4

Để làm tốt điều này, bạn thực sự cần một cái gì đó có chứa một C đầy đủ ++ trình phân tích cú pháp.

DMS Software Reengineering Toolkit với C++ Front End có thể được sử dụng cho việc này. Nó có thể cung cấp cả các khai báo thực thể chính xác bao gồm các kiểu và ngữ cảnh của chúng (lớp/không gian tên/...) và các vị trí tệp chính xác. DMS cung cấp quyền truy cập vào tất cả thông tin này dưới dạng tập hợp các AST và các bảng biểu tượng có liên quan; bạn xây dựng mã tùy chỉnh để điều hướng đến/lấy những gì bạn muốn.

Tùy theo nhu cầu của bạn, bạn có thể thấy rằng thông tin bạn muốn khó xử lý bằng cách sử dụng vanilla C#. Thông tin kiểu trong vinh quang đầy đủ của nó khá phức tạp, vì C++ là một ngôn ngữ phức tạp. Nếu bạn muốn xử lý thông tin đó, bạn sẽ muốn "ở bên trong" DMS, nơi tất cả các máy móc để làm điều đó là hiện tại. Nếu tất cả những gì bạn muốn là tên và loại thông tin dưới dạng chuỗi văn bản, bạn có thể nhận DMS để in ấn dữ liệu này trong biểu mẫu đó; nó có các thư viện chuẩn hỗ trợ các hoạt động đó. Câu trả lời trung gian sẽ là xuất dữ liệu ở định dạng XML; DMS cung cấp sự hỗ trợ trực tiếp cho việc xuất khẩu các đoạn AST tùy ý nhưng chỉ hỗ trợ gián tiếp cho việc viết thông tin kiểu như XML, nhưng sẽ không khó tùy chỉnh.

EDIT: (để trả lời bình luận OP trong câu trả lời khác) DMS có thể cung cấp thông tin chính xác cả về chữ ký phương thức và nội dung phương thức. Nó có đầy đủ thông tin AST và loại cho cả hai.

+0

Âm thanh tuyệt vời! Bây giờ tôi cần thông tin về giá cả ... làm thế nào tôi có thể liên lạc với u? – pablo

+0

Xem tiểu sử của tôi để biết địa chỉ email. Tất nhiên, luôn có chính trang web: -} –

+0

Liên kết đầu tiên của bạn bị hỏng: O (trên phản hồi này) – pablo

1

Nếu bạn muốn sử dụng Clang, tôi khuyên bạn nên xem this page. Nó chứng tỏ làm thế nào để có được tất cả các phương pháp ảo từ một tập tin. Một khi bạn hiểu ví dụ đơn giản này, bạn có thể tạo phức tạp hơn được gọi là matchers.

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