用MCA 8000A编写Linux驱动程序

To write Linux driver in MCA 8000A

本文关键字:Linux 驱动程序 编写 8000A MCA      更新时间:2023-10-16

该软件已经为Windows编写。我在想用Linux写它的好方法是什么。只需直接在Linux或更改Windows代码。

案例示例是National Instruments的MCA 8000A驱动程序,许多人试图为Linux编写该驱动程序,但没有成功,例如,由于嵌入效果更好,应用程序所需的硬件更少,最终目标是Raspberry Pi。

我开始通过将Windows文件转换为Linux来编写它,但我不确定这是否是一个好方法。

作者使用MCA 8000A中Linux驱动程序的一些变体

  • 认证科学软件
  • 一些用户

用于Raspberry Pi的MCA 8000A Linux驱动程序计划

以下代码来自API中记录的第一个链接。

他们的Pmcatest.cpp

#include <windows.h>           // Change
#include <stdio.h>
#include "PmcaCom.h"
#include "PmcaErr.h"
static int g_port;
static int g_baudRate;
static int g_gain;
static int g_scale;
static PmcaDeviceType g_device;
static PmcaFlagsType g_flags;
static PmcaStatusType g_status;
static char chBuff[32];
static unsigned long buff[16384];
#define MAX_MEMORY 32768
#define printf0(format) printf(format); fflush(stdout)
#define printf1(format, item) printf(format, item); fflush(stdout)
// command line: test <com port> <baud rate> <device type> <start gain>
// device type 0 - AUTO DETECT, 1 - PMCA 8000, 2 - PMCA 8000A 
int main(int argc, char *argv[])
{       
    ...
}

MicroTime.cpp

#if !defined(AFX_MICROTIME_H__495147C7_F0B7_11D1_B62F_9CFF0CC10000__INCLUDED_)
#define AFX_MICROTIME_H__495147C7_F0B7_11D1_B62F_9CFF0CC10000__INCLUDED_
#if _MSC_VER >= 1000
#pragma once
#endif // _MSC_VER >= 1000
class MicroTimeType  
{
    LARGE_INTEGER m_startTime;
    ...
public:
    MicroTimeType();
    LARGE_INTEGER GetCounter();
    ...
};
#endif // !defined(AFX_MICROTIME_H__495147C7_F0B7_11D1_B62F_9CFF0CC10000__INCLUDED_)

Queue.cpp

#include "windows.h"
#include "Queue.h"
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
QueueType::QueueType()
{
    ...
}
long QueueType::Put(QueueEntryType *entry)
{
    ...
}
QueueEntryType *QueueType::Get(void)
{
    ...
}
QueueEntryType *QueueType::LockedFind(long id)
{
   ...
}       
QueueEntryType *QueueType::Remove(long id)
{
   ...
}

Windows配置的其他代码

  • Pmcaex.cpp
  • 请求.cpp

如何在MCA8000A中编写Linux驱动程序?

打开源代码,我看到有一个名为dataprot.pdfMCA8000A USB Adapter Protocol.pdf的文件,它们都详细解释了数据协议如何在串行(RS-232)和USB总线上工作,以及PC和MCA的数据结构RX’d/TX’d;来自dataprot.pdf:The PC acts always as a master while the MCA responds always as a slave. The PC port output signal RTS is used by the PC to indicate the direction of the data transfer. RTS = HIGH indicates data transfer from PC to MCA (mode SEND), while RTS = LOW sets the data transfer direction from MCA to the PC (mode RECEIVE). The MCA constantly monitors the PC RTS line and responds accordingly. The action of the PC depends on the selected mode: SEND or RECEIVE. The DTR and DSR signals are used to synchronize the data streams from/to MCA8000A.

从来源本身来看,我没有看到任何太疯狂的东西;__declspec(dllimport/dllexport)之类的东西可以忽略,WaitForSingleObject可以用pthread_mutex_t替换(假设pthreads和用户空间模块,而不是完整的内核驱动程序),使用LARGE_INTEGERBYTE之类的类型可能会出现一些问题,因为它们可能是Windows平台特定的(32/64位类型),您可能必须用uint64_tunsigned char替换它们,像QueryPerformanceFrequency这样的东西可以用clock_gettime(CLOCK_MONOTONIC...)代替。。。尽管深入研究了源代码,但它似乎只不过是打开了设备的COM端口,并确保数据被打包在正确的结构中,以便代码用户执行"简单"的操作,如Receive(BYTE* buffer)WaitForDsrToggle。。

老实说,你有一个串行通信设备和它所规范的数据协议;您不需要进入内核,甚至不需要使用C或C++,shell脚本和管道重定向(或任何串行程序)将为您完成大量数据读取/写入(请注意,如果您遵守文档中的规范)。不过,这确实取决于你的需求;我使用shell脚本/管道重定向方法来测试我编写的嵌入式设备驱动程序(编写C内核驱动程序,闪存设备,在连接COM端口的情况下启动它,并等待开始用shell脚本敲击设备)。。不过,我不会将shell脚本作为驱动程序"发货"(如果你想做的不仅仅是与设备通信)。

希望这能有所帮助。

对于从Windows到Linux的数据类型转换,请将以下内容添加到适当的文件中,如下所述:

#include <stdint.h>
typedef uint8_t BYTE;
typedef uint32_t DWORD;
typedef int32_t LONG;
typedef int64_t LONGLONG;
typedef union _LARGE_INTEGER {
  struct {
    DWORD LowPart;
    LONG  HighPart;
  };
  struct {
    DWORD LowPart;
    LONG  HighPart;
  } u;
  LONGLONG QuadPart;
} LARGE_INTEGER, *PLARGE_INTEGER;