我们有一个用 VBA 编写的程序,它在Windows机器上运行。
我们有一个用 ANSI C 编写的非常相似的程序,使用Keil IDE 和在STR9x uP 上运行的编译器。
我们的计划是使用 C#在.NET中重写 VBA 代码。
用C++ 编写共享代码以在两个系统上使用的可行性是什么?显然,.NET 框架是不受限制的,但这不是什么大问题。具体来说,我想知道您认为编译过程的劳动密集程度如何。
我知道,这是一个理论问题,但感谢您的任何想法。
我这样做是一般做法。我认为比“是否有可能”更好的问题是“我应该如何构建我的代码以便能够在嵌入式系统和 PC 上运行”。
我更喜欢用 C 编写代码,并使用静态变量将每个文件构造为 c++ 类,以使全局变量对模块来说是私有的。创建 getter 和 setter 函数来访问私有变量。还使用我在模块初始化时为模块需要在模块外部调用的方法设置的函数指针。
从上述结构化的 c 代码重构为 c# 或 c++ 中的类也很容易。
您也可以直接使用 C++,但在嵌入式系统上使用不当可能会导致问题。
如果您要访问任何硬件,您将需要一个硬件抽象层。我将我的代码分为两种类型,第一种是没有引用它正在运行的代码的代码,另一种是我称为驱动程序的代码。
我使用此代码将模块重用于通信协议之类的事情。但更重要的是我用它来测试。我喜欢使用gtest对模块进行单元测试。我还可以重写驱动程序并在 PC 上模拟硬件,以便能够在 PC 上运行它。
显然,.NET 框架将不受限制
不一定是真的。给定足够的 ROM 和 RAM 资源(分别为 256K/64K),.NET Micro Framework将在您的设备上运行。但是,这不一定是使用它的好理由;嵌入式目标和 Windows 已经有另外两种常用的可移植语言:C 和 C++。C 和 C++ 所需的目标资源非常少 - C/C++ 运行时启动代码可以远低于 1K 的代码,几乎所有可用资源都可以由您的应用程序代码使用,而不是运行时环境。
在两个平台上使用通用代码的诀窍是抽象。如果您的目标使用任何类型的内核或调度程序(例如 RTOS 或线程库),这将至少涉及硬件抽象和可能的操作系统抽象。
我建议使用层架构设计您的嵌入式目标,至少有一个设备层和一个应用程序层,并且如前所述,如果使用,可能还有一个处理 IPC、同步和调度的系统层。您可能有其他更高层的接口,例如网络或文件系统,它们同样会从抽象中受益。请注意,BSD 套接字或 stdio 等标准 API 已经算作抽象,因此如果您的目标使用这些,您在 Windows 中要做的工作就会减少(BSD 套接字和 Winsock 之间的细微差别可能仍需要一些工作)
除了通过设备和系统层访问的那些之外,应用层将没有操作系统或硬件依赖。然后,您必须在 Windows 上将设备和系统层实现为模拟或重新映射到 Windows 上可用的服务或设备。一些 RTOS 已经包含用于测试和开发的 Windows 模拟器,但是定义您自己的 OS API 层,您可以在许多本机 RTOS 和 GPOS 之间移植,这将允许您的应用程序代码移植到不同的目标以进行模拟和实时执行非常迅速地。
如果平台差异很小且本地化,并且可能无法证明抽象层的合理性,那么目标特定的条件编译可能是合适的。编译器支持体系结构、操作系统或编译器特定代码的预定义宏,这些宏既可用于此本地化代码,也可在存在显着相似性的情况下使抽象层代码本身通用。