2012-03-16 2 views
2

Progress 9.1DアプリケーションとC言語関数とのやりとりが必要なプロジェクトで作業する必要があります。私はC関数の作成を担当しています。Progressの人々は、Progressテーブルを送信して、それを構造体としてC関数で受け取ることができるかどうか調査するように依頼しています。進捗状況4glとCの構造体

私はインターネットでいくつかの進行状況のマニュアル(Progress_External_Programming_Interfaces)を検索しましたが、これに関する情報はほとんど見つかりませんでした。私が理解しているように、テーブルはMEMPTR変数としてC関数に送信されるかもしれませんが、わかりません...

私はいくつかのチュートリアルやこれの例を教えてくれますか?

ありがとうございます。

答えて

1

プラットフォームに応じて、外部ライブラリを呼び出すことができますし、それを行う方法に関するドキュメントもあります(HLCコールと思われます)。あなたは10 *の十分最近のバージョンで作業していた場合

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

、取る可能性が考えられます。ライブラリにテーブル全体を送信することはできませんがに

、それは可能でしょうTT、それをMEMPTR内のXML構造に変換し、それをCコードに送信します。 V11.0のドキュメントについては

、それは「OE開発:プログラミングインタフェース」にあります「ホストレベルのコールインタフェース」の下のdoc

1

9.1Dは、当然のことながら、古代時代遅れとサポートされていないですが、それはありません、そうであってもDLLとしてCルーチンを呼び出すことをサポートします。いくつかの詳細な例については、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のユーザーが簡単に作業できるようにします。

最も単純な方法は、単純な単純なパラメータ(上記のような)を行うことです。おそらくあなたの機能が何をしているのかによっては、1つのレコードが一度に1つになる可能性があります。レコードのセットが必要な場合は、レコードを収集して何らかの形で管理する必要があります。

実際に構造体を作成してmemptrで構造体を構築する必要がある場合は、4GLのメンバーと密接に協力してAPIを定義し、memptrの外観に同意する必要があります。私はそれがたくさんの仕事になると思う - 私はそれを避け、私ができるならば簡単なパラメータで行く方法を見つけるだろう。

0

これはかなり簡単に行うことができますいずれかのティム・キューンやトム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などを参照)。

メモリ領域がProgressランタイムによって割り当てられ、C関数の呼び出し後すぐに解放されるため、覚えておきたいことがもう1つあります。これは、あなたが戻ってくるともう利用できなくなります。

  1. Timのソリューションは4GLの視点から実装するのが最も簡単ですが、CでXMLを解析する必要があり、他の2つのソリューションよりも大幅に多くのメモリを使用します。
  2. トムのソリューションは妥協です。データはバイナリ形式で送信されますが、4GL側でもう少し労力とスキルが必要です。 APIを公開し、状態を管理する必要があり、データは連続した複数の呼び出しで転送されます。
  3. 私が説明した解決策は、あなたが求めているものです。これにより、オーバーヘッドを最小限に抑えてデータを一度に渡すことができます。しかし、それは構成に依存するでしょう - あなたのCコンパイラによって生成された構造体のレイアウトは重要です。

他の問題は、第三の溶液を使用して、さまざまな文字列表現とエンコーディングに関する意味のある会話を持つことができるようにデータをマシンレベルでどのように表されるかを理解して4GL側の誰かが、エンディアン、パディング、進捗小数の表現を必要とすることですC言語では、精度の損失、日付の表現などがありません。明らかに、4GLの人々は、これらのトピックすべてで賢明ではない可能性があるソリューションを調査するように依頼したため、可能な限りタスクを簡素化し、それらの作業の大部分を行う方がよいでしょう。

もう1つの方法は、4GL側で適切なコンサルタントを雇って、この作業を徹底的に文書化することです。

さらに別の方法では、調査とプログラミング作業の大部分を自分でやっている間にStackoverflowで小さな質問を続けてください。私たちは喜んで手伝っていきます。がんばろう。

0

あなたが渡しているデータが巨大でない場合、9.1Dにはかなり良い基本的なDOMオブジェクトがあります。これは、Progress側でXMLでデータを構築するために使用します。それから私はそれをC関数に渡します。お使いのOSが何であるかはわかりませんが、Windowsでは、これをCOMオブジェクトまたはDLLにEXGLALを4GL内で簡単に渡すことができます(9.1D、11.0の制限により、.NET w/o GUI経由でこれを行うことができます)。私たちはLinuxや共有ライブラリを使って同じことをしました。 XMLメソッドは、オブジェクトを変更するための要件を削除します。また、AppServerを使用している場合は、ProxyGenツールを調べることもできます。

ドン。

関連する問題