From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-1.3 required=5.0 tests=BAYES_00,INVALID_MSGID autolearn=no autolearn_force=no version=3.4.4 X-Google-Language: ENGLISH,ASCII-7-bit X-Google-Thread: 103376,10dba3294c1a2195 X-Google-Attributes: gid103376,public From: tmoran@bix.com Subject: Re: New to ada95: porting Date: 2000/03/01 Message-ID: #1/1 X-Deja-AN: 591670838 References: <38BC5237.91FD3B95@mindspring.com> X-Complaints-To: abuse@pacbell.net X-Trace: news.pacbell.net 951899247 206.170.2.15 (Wed, 01 Mar 2000 00:27:27 PST) Organization: SBC Internet Services NNTP-Posting-Date: Wed, 01 Mar 2000 00:27:27 PST Newsgroups: comp.lang.ada Date: 2000-03-01T00:00:00+00:00 List-Id: If it doesn't cost too much in data copying, could you make a few wrapper functions to take the C results, copy the data into an Ada object, free the C allocated memory, and return the Ada object, along the lines: type A is array(index_type <>) of some_element; function Wrapped_C_Fun(Params:whatever) return A is use System.Storage_Elements; Dope_Offset : constant Storage_Offset := 16; -- 128/8 bit Storage_Elements type Dummy_A is A(0 .. index_type'last); -- fixed, though large, size package Addr_Acc_Dummy_A is new System.Address_To_Access_Conversions(Dummy_A); type C_Returned_Ptr_Type is access Dummy_A; function C_Fun(Params:whatever) return C_Returned_Ptr_Type; pragma Import(C, C_Fun, "CFun"); Data_Ptr : C_Returned_Ptr_Type := C_Fun(Params); -- call the C function Data_Address : constant System.Address := Addr_Acc_Dummy_A.To_Address(Data_Ptr); Dope_Address : constant System.Address := Dope_Address - Dope_Offset; type Dope is record Size, Lower_Bound, Upper_Bound, Byte_Count : Integer; Data : Dummy_A; end record; for Dope use Size at 0 range 0 .. 31; Lower_Bound at 4 range 0 .. 31; Upper_Bound at 8 range 0 .. 31; Byte_Count at 12 range 0 .. 31; Data at 16 range 0 .. (index_type'last+1)*some_element'size-1; end record; type Dope_Ptr_Type is access Dope; package Addr_Acc_Dope is new System.Address_To_Access_Conversions(Dope_Ptr_Type); Dope_Ptr : constant Dope_Ptr_Type := Addr_Acc_Dope.To_Access(Dope_Address); Result : A(Dope_Ptr.Lower_Bound .. Dope_Ptr.Upper_Bound); begin if Dope_Ptr.Size /= some_element'size then raise an_exception;end if; if Dope_Ptr.Byte_Count /= Result'size/8 then raise an_exception;end if; -- first copy the returned array from the C structure to an A. Result := Data_Ptr.all(0 .. Result'length-1); -- free the C memory C_Free(Dope_Ptr); -- return result of type A. return Result; end Wrapped_C_Fun; Note: this code untested and written after midnight.