qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
From: John Snow <jsnow@redhat.com>
To: Markus Armbruster <armbru@redhat.com>
Cc: "Marc-André Lureau" <marcandre.lureau@redhat.com>,
	"Cleber Rosa" <crosa@redhat.com>,
	qemu-devel@nongnu.org, "Eduardo Habkost" <ehabkost@redhat.com>
Subject: Re: [PATCH 08/12] qapi/schema: make QAPISourceInfo mandatory
Date: Thu, 17 Dec 2020 12:02:29 -0500	[thread overview]
Message-ID: <e9f43898-1c0b-54e3-59a7-d9064c2d86ea@redhat.com> (raw)
In-Reply-To: <87pn38lv1d.fsf@dusky.pond.sub.org>

On 12/17/20 3:02 AM, Markus Armbruster wrote:
> John Snow <jsnow@redhat.com> writes:
> 
>> On 12/16/20 5:18 AM, Markus Armbruster wrote:
>>> John Snow <jsnow@redhat.com> writes:
>>>
>>>> --
>>>>
>>>> events.py had an info to route, was it by choice that it wasn't before?
>>>
>>> See below.
>>>
>>> I figure this is intentionally below the -- line, but ...
>>>
>>>> Signed-off-by: John Snow <jsnow@redhat.com>
>>>
>>> ... this should be above it.
>>>
>>
>> Script failure. Or human failure, because I used '--' instead of '---'.
>>
>>>> ---
>>>>    scripts/qapi/events.py |  2 +-
>>>>    scripts/qapi/schema.py | 23 +++++++++++++----------
>>>>    scripts/qapi/types.py  |  9 +++++----
>>>>    scripts/qapi/visit.py  |  6 +++---
>>>>    4 files changed, 22 insertions(+), 18 deletions(-)
>>>>
>>>> diff --git a/scripts/qapi/events.py b/scripts/qapi/events.py
>>>> index 9851653b9d11..9ba4f109028d 100644
>>>> --- a/scripts/qapi/events.py
>>>> +++ b/scripts/qapi/events.py
>>>> @@ -225,7 +225,7 @@ def visit_event(self,
>>>>                                              self._event_emit_name))
>>>>            # Note: we generate the enum member regardless of @ifcond, to
>>>>            # keep the enumeration usable in target-independent code.
>>>> -        self._event_enum_members.append(QAPISchemaEnumMember(name, None))
>>>> +        self._event_enum_members.append(QAPISchemaEnumMember(name, info))
>>>
>>> We pass None because errors should never happen, and None makes that
>>> quite clear.
>>>
>>
>> Not clear: *why* should errors never happen? This is the only place we
>> pass None for SourceInfo that isn't explicitly a literal built-in type.
>> This is not obvious.
> 
> You're right, but there are two separate "unclarities".
> 
> Passing None effectively asserts "errors never happen".  We neglect to
> explain why, leaving the reader guessing.
> 
> Passing @info "fixes" that by removing the assertion.  Now we have a
> more subtle problem: will errors make sense with this @info?  Normally,
> all members of an enum share one info.  Only this enum's members don't.
> It turns out the question is moot because @info is not actually used.
> But will it remain moot?  My point isn't that these are important
> questions to answer.  It is that we're replacing the relatively obvious
> question "why are we asserting errors can't happen" by more subtle ones.
> Feels like sweeping dirt under the rug.
> 

I'll grant you that. I'm going wide instead of deep, here. There were 
200+ errors to fix, and not every last one got the same level of attention.

I definitely did just sweep some dirt under the rug.

>>> We don't actually have a built-in QAPISchemaEnumType for the event enum.
>>> We merely generate a C enum QAPIEvent along with macro QAPIEvent_str(),
>>> by passing self._event_emit_name, self._event_enum_members straight to
>>> gen_enum() and gen_enum_lookup().
>>>
>>> If we did build a QAPISchemaEnumType, and used it to diagnose clashes,
>>> then clashes would be reported like
>>>
>>>       mumble.json: In event 'A-B':
>>>       mumble.json: 2: value 'A-B' collides with value 'A_B'
>>>
>>> leaving you guessing what "value" means, and where 'A_B' may be.
>>>
>>> Bug: we don't diagnose certain event name clashes.  I'll fix it.
>>>
>>
>> Not clear to me: If I want interface consistency, what *should* be
>> passed downwards as the info? it's not quite a builtin as much as it is
>> an inferred enum,
> 
> True.
> 
>>                    so should I just ... leave it like this, or wait for
>> you to offer a better fix?
> 
> Waiting for some better fix feels undavisable.  We want to get type
> checking in place sooner rather than later.
> 

OK. You mentioned fixing the conflicts, so I had thought maybe that was 
near-term instead of long-term. We have cleared that misunderstanding up ;)

> Aside: a possible fix is decoupling gen_enum_lookup() and gen_enum()
> from QAPISchemaEnumMember, so we don't have to make up
> QAPISchemaEnumMembers here.
> 

I'm not sure I have the broader picture here to do this, or the time to 
focus on it. It's a bit of a deeper fix than the rest of the minor 
refactorings I do in these series.

> I think there are two interpretations of your QAPISourceInfo work's aim:
> 
> 1. Narrow: use a special QAPISourceInfo rather then None as "no errors
>     shall happen" poison.
> 
>     QAPISourceInfo.builtin() returns this poison.  The name "builtin" is
>     less than ideal.
> 

I did intend it to be used for explicit built-in types; this is an 
"inferred" type, and I'd use a differently named poison for it, I suppose.

> 2. Ambitious: eliminate "no errors shall happen".
> 
> We're discussing this in reply of PATCH 06.  I think we need to reach a
> conclusion there before we can decide here.
> 

OK, I'll head over there. I'm still a bit confused over here, but we'll 
get to it.


>>>>    
>>>>    
>>>>    def gen_events(schema: QAPISchema,
>>>> diff --git a/scripts/qapi/schema.py b/scripts/qapi/schema.py
>>>> index 720449feee4d..d5f19732b516 100644
>>>> --- a/scripts/qapi/schema.py
>>>> +++ b/scripts/qapi/schema.py
>>>> @@ -23,6 +23,7 @@
>>>>    from .error import QAPIError, QAPISemError
>>>>    from .expr import check_exprs
>>>>    from .parser import QAPISchemaParser
>>>> +from .source import QAPISourceInfo
>>>>    
>>>>    
>>>>    class QAPISchemaEntity:
>>>> @@ -36,10 +37,10 @@ def __init__(self, name, info, doc, ifcond=None, features=None):
>>>>            self.name = name
>>>>            self._module = None
>>>>            # For explicitly defined entities, info points to the (explicit)
>>>> -        # definition.  For builtins (and their arrays), info is None.
>>>> -        # For implicitly defined entities, info points to a place that
>>>> -        # triggered the implicit definition (there may be more than one
>>>> -        # such place).
>>>> +        # definition.  For builtins (and their arrays), info is a null-object
>>>> +        # sentinel that evaluates to False. For implicitly defined entities,
>>>> +        # info points to a place that triggered the implicit definition
>>>> +        # (there may be more than one such place).
>>>
>>> s/builtins/built-in types/
>>>
>>> The meaning of "a null object sentinel" is less than clear.  Perhaps "a
>>> special object".
>>>
>>
>> OK.
>>
>>>>            self.info = info
>>>>            self.doc = doc
>>>>            self._ifcond = ifcond or []
>>>> @@ -209,7 +210,7 @@ class QAPISchemaBuiltinType(QAPISchemaType):
>>>>        meta = 'built-in'
>>>>    
>>>>        def __init__(self, name, json_type, c_type):
>>>> -        super().__init__(name, None, None)
>>>> +        super().__init__(name, QAPISourceInfo.builtin(), None)
>>>>            assert not c_type or isinstance(c_type, str)
>>>>            assert json_type in ('string', 'number', 'int', 'boolean', 'null',
>>>>                                 'value')
>>>> @@ -871,7 +872,7 @@ def resolve_type(self, name, info, what):
>>>>            return typ
>>>>    
>>>>        def _module_name(self, fname):
>>>> -        if fname is None:
>>>> +        if not fname:
>>>>                return None
>>>>            return os.path.relpath(fname, self._schema_dir)
>>>>    
>>>
>>> Sure this hunk belongs to this patch?
>>>
>>
>> Accident.
>>
>> "info and info.fname" does not behave the same with a falsey info object
>> as it does when info was genuinely None; I compensated for that *here*,
>> but I should have compensated for it elsewhere.
>>
>>>> @@ -897,9 +898,11 @@ def _def_builtin_type(self, name, json_type, c_type):
>>>>            # be nice, but we can't as long as their generated code
>>>>            # (qapi-builtin-types.[ch]) may be shared by some other
>>>>            # schema.
>>>> -        self._make_array_type(name, None)
>>>> +        self._make_array_type(name, QAPISourceInfo.builtin())
>>>>    
>>>>        def _def_predefineds(self):
>>>> +        info = QAPISourceInfo.builtin()
>>>> +
>>>
>>> Everything else gets its very own copy of the "no source info" object,
>>> except for the stuff defined here, which gets to share one.  Isn't that
>>> odd?
>>>
>>
>> It's also the only function where we define so many built-ins in the
>> same place, so spiritually they do have the same SourceInfo, right? :)
>>
>> (OK, no, it wasn't a conscious design choice, but it also seems
>> harmless. I am going to assume you'd prefer I not do this?)
> 
> It is harmless.  It just made me wonder why we create more than one such
> QAPISourceInfo in the first place.  Method builtin() could return the
> same one every time.  It could even be an attribute instead of a method.
> Anyway, no big deal.
> 

I could conceivably use source line information and stuff, to be 
needlessly fancy about it. Nah. I just think singleton patterns are kind 
of weird to implement in Python, so I didn't.

--js



  reply	other threads:[~2020-12-17 17:22 UTC|newest]

Thread overview: 41+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-12-14 23:53 [PATCH 00/12] qapi: static typing conversion, pt1.5 John Snow
2020-12-14 23:53 ` [PATCH 01/12] qapi/commands: assert arg_type is not None John Snow
2020-12-14 23:53 ` [PATCH 02/12] qapi/events: fix visit_event typing John Snow
2020-12-14 23:53 ` [PATCH 03/12] qapi/main: handle theoretical None-return from re.match() John Snow
2020-12-16  8:23   ` Markus Armbruster
2020-12-16 17:11     ` John Snow
2020-12-14 23:53 ` [PATCH 04/12] qapi/gen: assert that _start_if is not None in _wrap_ifcond John Snow
2020-12-16  8:26   ` Markus Armbruster
2020-12-16 17:13     ` John Snow
2020-12-17  7:24       ` Markus Armbruster
2020-12-14 23:53 ` [PATCH 05/12] qapi/gen: use './builtin' for the built-in module name John Snow
2020-12-16  8:35   ` Markus Armbruster
2020-12-16 17:27     ` John Snow
2020-12-14 23:53 ` [PATCH 06/12] qapi/source: Add builtin null-object sentinel John Snow
2020-12-16  9:22   ` Markus Armbruster
2020-12-16 17:53     ` John Snow
2020-12-17 12:33       ` Markus Armbruster
2020-12-18 19:14         ` John Snow
2020-12-16 19:11     ` John Snow
2020-12-17 11:56       ` Markus Armbruster
2020-12-18 19:22         ` John Snow
2020-12-14 23:53 ` [PATCH 07/12] qapi/gen: write _genc/_genh access shims John Snow
2020-12-14 23:53 ` [PATCH 08/12] qapi/schema: make QAPISourceInfo mandatory John Snow
2020-12-16 10:18   ` Markus Armbruster
2020-12-16 18:41     ` John Snow
2020-12-17  8:02       ` Markus Armbruster
2020-12-17 17:02         ` John Snow [this message]
2020-12-18  5:24           ` Markus Armbruster
2020-12-18 19:17             ` John Snow
2020-12-18 20:57               ` Markus Armbruster
2020-12-18 21:30                 ` John Snow
2020-12-14 23:53 ` [PATCH 09/12] qapi/gen: move write method to QAPIGenC, make fname a str John Snow
2020-12-16 10:31   ` Markus Armbruster
2020-12-14 23:53 ` [PATCH 10/12] tests/qapi-schema: Add quotes to module name in test output John Snow
2020-12-14 23:53 ` [PATCH 11/12] qapi/schema: Name the builtin module "" instead of None John Snow
2020-12-16 10:42   ` Markus Armbruster
2020-12-16 18:57     ` John Snow
2020-12-17 11:09       ` Markus Armbruster
2020-12-17 21:07         ` John Snow
2020-12-18  5:31           ` Markus Armbruster
2020-12-14 23:53 ` [PATCH 12/12] qapi: enable strict-optional checks John Snow

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=e9f43898-1c0b-54e3-59a7-d9064c2d86ea@redhat.com \
    --to=jsnow@redhat.com \
    --cc=armbru@redhat.com \
    --cc=crosa@redhat.com \
    --cc=ehabkost@redhat.com \
    --cc=marcandre.lureau@redhat.com \
    --cc=qemu-devel@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).