I have:
(in-package #:de.consequor.app.core.platform.cross-platform)
(defctype uint64_t :unsigned-long-long)
and:
(in-package #:de.consequor.app.core.platform.osx.i386)
(defctype mach_vm_address_t uint64_t)
Guess what? The second defctype doesn't see the first defctype:
Unknown CFFI type: CCAG.OSX.I386::UINT64_T.
(CCAG.OSX.I386 is the nickname of
#:de.consequor.app.core.platform.osx.i386)
Any hints? (I know I'm doing something wrong, but ...)
TIA!
Regards
Frank
Actually, you are using two different symbols for uint64_t:
de.consequor.app.core.platform.cross-platform:uint64_t
and
de.consequor.app.core.platform.osx.i386:uint64_t.
(defctype mach_vm_address_t de.consequor.app.core.platform.cross-
platform:uint64_t) should work.
> (in-package #:de.consequor.app.core.platform.cross-platform)
>
> (defctype uint64_t :unsigned-long-long)
At this point uint64_t is interned into ...cross-platform (unless it's
already accessible somehow).
> (in-package #:de.consequor.app.core.platform.osx.i386)
>
> (defctype mach_vm_address_t uint64_t)
At this point entirely unrelated symbol (though also named uint64_t) is
interned into ...i386 package.
> Guess what? The second defctype doesn't see the first defctype:
It probably would, if only they /had/ the same name.
Now, of course, I can be deadly wrong -- if you are taking care to make
the same uint64_t accessible in both packages. E.g. one of the packages
could have an :import-from option requesting this explicitly.
If you try the following in your REPL:
(in-package #:de.consequor.app.core.platform.cross-platform)
(describe 'uint64_t)
(in-package #:de.consequor.app.core.platform.osx.i386)
(describe 'uint64_t)
it's likely to become immediately visible whether you have two distinct
symbols or one symbol accessible everywhere.
--
Regards, Anton Kovalenko
+7(916)345-34-02 | Elektrostal' MO, Russia
Actually, I would recommend to use :uint64 (that names a built-in type
for CFFI) instead of the above definition. A possible reason not to use
:uint64 would be there if you were building some abstraction that would
hide platform differences, but then you won't have `64' in your type
names.
> (in-package #:de.consequor.app.core.platform.cross-platform)
> (describe 'uint64_t)
> (in-package #:de.consequor.app.core.platform.osx.i386)
> (describe 'uint64_t)
Amending myself: more straightforward way to test it would be
(eq 'something...cross-platform::uint64_t
'something...i386::uint64_t)
Yep, thanks. I had assumed (I know, one shouldn't "assume") that CFFI
defines its own namspace and make any defctype'd type know to any CFFI
defintion. It doesn't. So I am using :uint64 now. Works.
Thanks.
- Frank
>> (eq 'something...cross-platform::uint64_t
>> 'something...i386::uint64_t)
>
> Yep, thanks. I had assumed (I know, one shouldn't "assume") that CFFI
> defines its own namspace and make any defctype'd type know to any CFFI
> defintion. It doesn't. So I am using :uint64 now. Works.
(This post may look like nitpicking with no immediate bearing on the
CFFI case in hand, but it can probably help with expecting the right
thing next time, so:)
CFFI /has/ its own namespace for type definitions, in the LispN[1]
sense: we have variables, functions and classes named by symbols, and
CFFI adds another member to this family.
With things named by symbols, and symbols are named by strings, we have
to deal with two /orthogonal/ namespace partitions: packages come into
play (only) at the string->symbol stage, and the context where the
symbol is used determines the LispN-namespace. Thus adding a new
namespace to the latter set doesn't result in any conflation of symbols
within packages.
How can there be an expectation that packages will go away when a new
namespace is introduced? Well, if something is named directly by strings
(as opposed to symbols), /and/ when string designators are accepted,
too, it may cause this wrong kind of intuition to develop -- especially
if most existing code dealing with such things avoids strings and goes
for designators. One obvious example (from the standard) are packages;
another example (outside the standard) are system definitions.
There are reasons to prefer (:use :common-lisp) or (:use #:common-lisp)
to (:use "COMMON-LISP"), but if one doesn't see the latter variant for
some time, he may be inclined to think of it as "namespace with symbols
as names, but with package disregarded". Some habit of `seeing through'
the string designators may be an antidote: when a funny ways to
designate "COMMON-LISP" are perceived as such, it becomes pretty obvious
that no package conflation happens here. OTOH, when you encounter a
documented interface (like CFFI) that specifies something as "named by
symbols", with no mention of strings or string designators, that fact
alone produces the expectation that packages /don't/ go away.
Footnotes:
[1] Where I find helpful to think of "N" as standing for "namespaced",
and not just for some i>1.