进步4gl和C结构

时间:2012-03-16 17:39:03

标签: c progress-4gl

我需要在涉及Progress 9.1D应用程序和C语言函数之间的交互的项目中工作。我负责编写C函数,Progress人员让我调查是否可以发送Progress表并在C函数中作为结构接收它。

我已经在互联网上搜索了几天和一些进度手册(Progress_External_Programming_Interfaces)但我发现的信息很少。据我所知,该表可能作为MEMPTR变量发送到C函数,但我不确定......

拜托,有人可以指点一些教程或者这个例子吗?

非常感谢。

4 个答案:

答案 0 :(得分:1)

根据您的平台,可以调用外部库,并且有关于如何执行此操作的文档(我认为是HLC调用)。

虽然不可能将整个表发送到库,但是可以:

 FOR EACH table-name NO-LOCK:
    /* transfer table data to memptr */
    /* make C call */
    /* interpret results */
 END.

如果您使用的是10. *的最新版本,则可以使用TT,将其转换为MEMPTR中的XML结构,然后将其发送到C代码。

对于V11.0文档,它位于“主机级调用接口”下的“OE开发:编程接口”文档中

答案 1 :(得分:1)

9.1D当然是古老的,过时的和不受支持的,但即便如此,它确实支持将C例程作为DLL来调用。对于一些详细示例,您可能会发现UNIX Shared Libraries上的此演示文稿很有帮助。 (血腥的细节各不相同,但如果这是你的环境,那么相同的想法适用于Windows。)

4GL方面的简单例子:

define variable x as integer no-undo.
define variable c as memptr  no-undo.
define variable m as memptr  no-undo.

procedure sprintf external "/lib64/libc.so.6":
  define input-output parameter fStr as memptr.
  define input  parameter mask as memptr.
  define input  parameter arg  as double.
  define return parameter x    as long.
end.

set-size( c ) = 1024.
set-size( m ) = 1024.
put-string( m, 1 ) = "%1.4e".
run sprintf( input-output c, m, 0.0123, output x ).

display get-string( c, 1 ) format “x(20)”.

return.

作为C程序员,您的主要问题是提供一个API和数据结构,4GL人员可以轻松使用。

最简单的方法是只做简单的旧简单参数(如上所述)。可能一次只有一条记录(取决于你的功能正在做什么可能,或者可能没有意义 - 如果你需要一组记录可以使用,那么你需要收集它们并以某种方式管理它们。)

如果确实需要创建结构并使用memptrs构建它们,那么您将不得不与4GL人员密切合作来定义API并同意memptr应该是什么样子。我认为这可能需要做很多工作 - 如果可以的话,我会尽量避免使用简单的参数。

答案 2 :(得分:0)

这可以很容易地完成:无论是Tim Kuehn还是Tom Bascom建议,还是:

分配足够大的内存区域来保存数据:

def var mp as memptr no-undo.
set-size(mp) = 1024. /* pre-calculated size depending on the data, in bytes */
/* copy contents of temp-table into mp */
run procedureInC (mp). /* run external procedure */
set-size(mp) = 0.    /* free up the memory */

需要填写三件主要内容:

  1. 决定如何在内存区域内构建数据,这包括就如何表示4GL数据类型(即字符串的表示和长度,小数,日期等)和良好理解how your particular C compiler lays out structs in memory达成一致。
  2. 一旦有关于第一点的协议,4GL人就可以推出一个函数,给定一个临时表句柄将根据使用第1点和记录数计算的记录大小来计算所需的内存区域大小。
  3. 接下来4GL人员可以按照第1点中约定的规则推出一个将临时表复制到内存区域的程序(查看PUT-BYTE,PUT-STRING等进展手册)。
  4. 还有一件事需要记住,因为内存区域将由Progress运行时分配,然后在调用C函数后直接释放,您需要复制内容,因为它不会是任何内容一旦你回来就可以延长。

    1. Tim的解决方案从4GL的角度来看是最简单的实现,但你需要在C中解析XML,它将比其他两个解决方案使用更多的内存。
    2. 汤姆的解决方案是妥协。数据以二进制形式发送,但是在4GL方面需要更多的努力和技巧。您需要推出一个API,管理状态,并且数据将在多个连续的呼叫中传输。
    3. 我描述的解决方案就是你所要求的。它允许以最小的开销一次性传递数据。但是,它将取决于配置 - C编译器生成的结构布局很重要。
    4. 另一个问题是,第三个解决方案需要4GL方面的某个人了解如何在机器级别上表示数据,这样您就可以进行有关各种字符串表示和编码的有意义的对话,字节顺序,填充,C中的进度小数表示精度损失,日期表示等。显然,由于4GL人员要求您调查他们可能不熟悉所有这些主题的解决方案,因此您最好尽可能简化他们的任务并为他们完成大部分工作。

      另一种方法是聘请4GL方面的合适顾问来为您完成这项工作。

      另一种方法是继续在Stackoverflow上提出较小的问题,同时自己进行大量的调查和编程工作 - 我们很乐意提供帮助。祝你好运。

答案 3 :(得分:0)

如果您传递的数据不是很大,9.1D有一个相当不错的基本DOM对象,我将在Progress端使用它来构建我的XML数据。然后我将它传递给C函数。不确定你的操作系统是什么,但是在Windows中你可以使用4GL中的EXTERNAL轻松地将它传递给COM对象或DLL(因为9.1D,11.0的限制允许你通过.NET w / o GUI来实现)。我们使用Linux和共享库完成了同样的事情。 XML方法消除了更改对象的要求。如果您使用的是AppServer,也可以查看ProxyGen工具。

唐。