comp.lang.ada
 help / color / mirror / Atom feed
From: "Dmitry A. Kazakov" <mailbox@dmitry-kazakov.de>
Subject: Re: Accessing Addresses in a Passed String
Date: Sat, 1 Jan 2022 21:16:11 +0100	[thread overview]
Message-ID: <sqqcq9$15rk$1@gioia.aioe.org> (raw)
In-Reply-To: 39e6c150-e377-46a9-8140-fae57b9b2599n@googlegroups.com

On 2022-01-01 20:40, Pat Van Canada wrote:

> Thanks. So here is what I am playing around with. There is an ncurses Ada binding and a binding to a the Forms library but I am trying to do something a little different.

[ Of course, the right solution would be to remove ncurses from all 
available computers. (:-)) ]

> The basic problem is to collect user input and assign characters back to many string variables in one go.

It is irrelevant. You need to learn how this abomination works. There 
are many scenarios of how a C library could treat a "string" [C does not 
have them]:

1. The caller maintains the string.

2. The caller passes ownership to the callee, which means that at some 
point C will call free() on the pointer and also that the string must be 
allocated using C malloc() or some library-specific allocator. Many 
problem-specific libraries actually go this way.

In the scenario #1 the callee can:

1.1. Stop using the string after returning.

1.2. Keep on using it in consequent calls or asynchronously, which means 
that the caller may not destroy the string until the library indicates 
or implicates that the string is no more in use.

Well-designed C libraries tend to #1.1, of course.

The second stop is to know how the abomination determines the string length:

A. Nul-terminated

B. Extra parameter with the character count

For #1.1.A you must use function To_C that will create a nul-terminated 
C string from Ada string or a slice of:

    To_C (Text (I..I+22))

and char_array in the bindings.

For #1.1.B you can do the same or else trick GNAT compiler using 
System.Address in place of char * in the bindings. It works well with 
GNAT. E.g. instead of declaring

    function strncpy (dest : chars_ptr; src : char_array; n : size_t)
       return chars_ptr;
    pragma Import (C, strncpy);

You can declare it as

    function strncpy (dest : chars_ptr; src : Address; n : size_t)
       return chars_ptr;
    pragma Import (C, strncpy);

and use with a slice Text (I..I+22) like this:

    strncpy (Target, Text (I)'Address, 23)

> I want to call a procedure to load each string into an intermediate data structure but I do not want to have to pass them all back to have their values to be updated. I figured with the screen co-ordinates and addresses I could avoid this.

Again, that depends on the way the abomination works. I would guess #1.1 
But if it is #1.2 you would have much fun in your hands.

> I don't really want to start with pointer arithmetic or similar but I also need the strings to have their values updated without the second batch of passing .

The standard Ada library provides ready-to-use packages for that, but 
normally you never need that for interfacing well-designed C libraries.

-- 
Regards,
Dmitry A. Kazakov
http://www.dmitry-kazakov.de

  reply	other threads:[~2022-01-01 20:16 UTC|newest]

Thread overview: 9+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-01-01 18:53 Accessing Addresses in a Passed String Pat Van Canada
2022-01-01 19:23 ` Dmitry A. Kazakov
2022-01-01 19:40   ` Pat Van Canada
2022-01-01 20:16     ` Dmitry A. Kazakov [this message]
2022-01-01 23:03       ` Pat Van Canada
2022-01-01 20:57 ` Niklas Holsti
2022-01-01 23:37   ` Pat Van Canada
2022-01-02 13:15   ` Pat Van Canada
2022-01-02 14:41   ` Pat Van Canada
replies disabled

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox