All of lore.kernel.org
 help / color / mirror / Atom feed
From: Stefan Weil <weil@mail.berlios.de>
To: "Michael S. Tsirkin" <mst@redhat.com>
Cc: qemu-devel@nongnu.org
Subject: [Qemu-devel] Re: [RFC] API change for pci_set_word and related functions
Date: Mon, 11 Jan 2010 20:38:53 +0100	[thread overview]
Message-ID: <4B4B7E4D.5010101@mail.berlios.de> (raw)
In-Reply-To: <20100111183437.GA13712@redhat.com>

Michael S. Tsirkin schrieb:
> On Thu, Jan 07, 2010 at 04:07:26PM +0100, Stefan Weil wrote:
>> Michael S. Tsirkin schrieb:
>>> On Thu, Jan 07, 2010 at 12:15:25PM +0100, Stefan Weil wrote:
>>> ...
>>>> ---
>>>> hw/eepro100.c | 4 +---
>>>> 1 files changed, 1 insertions(+), 3 deletions(-)
>>>>
>>>> diff --git a/hw/eepro100.c b/hw/eepro100.c
>>>> index 336ca49..a21c984 100644
>>>> --- a/hw/eepro100.c
>>>> +++ b/hw/eepro100.c
>>>> @@ -420,10 +420,8 @@ static void pci_reset(EEPRO100State * s)
>>>> /* TODO: this is the default, do not override. */
>>>> PCI_CONFIG_16(PCI_COMMAND, 0x0000);
>>>> /* PCI Status */
>>>> - /* TODO: this seems to make no sense. */
>>>> /* TODO: Value at RST# should be 0. */
>>> So this second todo can go too. I've removed it in my tree.
>>>
>>>> - PCI_CONFIG_16(PCI_STATUS,
>>>> - PCI_STATUS_REC_MASTER_ABORT | PCI_STATUS_SIG_TARGET_ABORT);
>>>> + PCI_CONFIG_16(PCI_STATUS, PCI_STATUS_DEVSEL_MEDIUM |
>>>> PCI_STATUS_FAST_BACK);
>>>> /* PCI Revision ID */
>>>> PCI_CONFIG_8(PCI_REVISION_ID, 0x08);
>>> BTW if you are not afraid of churn, there's no reason
>>> for PCI_CONFIG_8 and friends anymore, because pci.h
>>> has much nicer pci_set_byte etc.
>> Hello Michael,
>>
>> I already noticed pci_set_byte, pci_set_word, pci_set_long and
>> the corresponding pci_get_xxx functions and thought about using them.
>>
>> I did not start it because I want to suggest a different API
>> for use in PCI device emulations:
>>
>> instead of
>>
>> pci_set_word(pci_conf + PCI_STATUS, PCI_STATUS_CAP_LIST);
>>
>> or
>>
>> pci_set_word(&pci_conf[PCI_STATUS], PCI_STATUS_CAP_LIST);
>>
>> it would be better to call
>>
>> pci_set_word(pci_conf, PCI_STATUS, PCI_STATUS_CAP_LIST);
>>
>>
>> The prototypes would look like this:
>>
>> /* Set PCI config value. */
>> void pci_set_word(PCIDevice *s, uint8_t offset, uint16_t val);
>>
>> /* Set PCI cmask value. */
>> void pci_set_cmask_word(PCIDevice *s, uint8_t offset, uint16_t val);
>>
>> /* Set PCI wmask value. */
>> void pci_set_wmask_word(PCIDevice *s, uint8_t offset, uint16_t val);
>>
>> What are the advantages?
>> * strict type checking (the old API takes any uint8_t *)
>
> So IMO it's easier to make mistakes with your proposed API because if
> you confuse offset and value compiler does not complain. More
> importantly, if you want to pass some other uint8_t pointer to e.g.
> pci_set_word, you can *and nothing unexpected will happen*
> it will set the word to the given value. So the current
> API is more type safe than what you propose.
>

No. The current API takes any uint8_t pointer to read or write
a value. This is not safe.

The proposed API only takes a PCIDevice pointer
and reads or writes only configuration (or cmask or
wmask) values. Yes, you can take offset for value.
If you are lucky and value is an uint16_t or uint32_t,
your compiler will complain. And even if your compiler
does not complain, it is wrong but still safe, because
the code will only access the PCI configuration data.


>> * many other pci_* functions also have a first parameter of type PCIDevice
>
> So what would make sense IMO is higer level abstraction,
> for example similar to what we have with capabilities
> and msix, I think we could have something like this
> for e.g. power management.
>
> For low-level bit tweaking, the advantages of current API is that same
> thing can be used to set wmask, cmask, config itself, and whatever else
> we will come up with.

The low level API can be used where low level is
adequate: in pci.c for example.

To implement emulated PCI devices, a more robust API
would be better. Think of the number of devices which
are still missing, think of people who want to write
a new PCI device emulation for QEMU without being
a QEMU expert.

>
>> * calls look nicer (at least in my opinion)
>
> What I value is the fact that it's obvious which
> data is changed.

Here there is no difference between current and
proposed API:

old: pci_set_word(&pci_conf[PCI_STATUS], PCI_STATUS_CAP_LIST);
new: pci_set_word(pci_conf, PCI_STATUS, PCI_STATUS_CAP_LIST);

Every function call hides what happens. If you really wanted
to see which data is changed, you would have to write

*(uint16_t *)&pci_conf[PCI_STATUS] = cpu_to_le16(PCI_STATUS_CAP_LIST);

>
>> * strict range checking (offset is limited to 0...255, additional
>>   assertions possible - the old API is unsafe because it just takes
>>   a pointer)
>
> I don't think we want to add return status, so there wouldn't
> be a benefit to range checking as we can't act on it.
> Anyway, it's very unusual to use anything but a constant
> as an offset, so range errors are very uncommon.

There is an implicit range checking in the proposed
API because the offset is uint8_t, so it cannot
exceed the range which is valid for configuration
offsets.

A more elaborated check could require that
configuration byte values are only addressed
using pci_set_byte (not pci_set_long)
and raise a fatal runtime error otherwise.

Runtime checks without return values
are well established in QEMU's code,
and they are very useful for code writers.

>
>> The functions are inline, so the resulting code won't differ.
>>
>> Instead of _byte, _word and _long I personally prefer something
>> like _8, _16, _32 because _word and _long need interpretation.
>> But this is only a matter of taste - the API change is more important.
>>
>>
>> Regards,
>>
>> Stefan Weil

  reply	other threads:[~2010-01-11 19:39 UTC|newest]

Thread overview: 34+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <cover.1260466626.git.mst@redhat.com>
2009-12-10 18:09 ` [Qemu-devel] [PATCH 01/17] e1000: switch to symbolic names for pci registers Michael S. Tsirkin
2009-12-10 18:09 ` [Qemu-devel] [PATCH 02/17] ne2000: " Michael S. Tsirkin
2009-12-10 18:09 ` [Qemu-devel] [PATCH 03/17] rtl: " Michael S. Tsirkin
2009-12-10 18:10 ` [Qemu-devel] [PATCH 04/17] pcnet: " Michael S. Tsirkin
2009-12-10 18:10 ` [Qemu-devel] [PATCH 05/17] pci: add more status bits Michael S. Tsirkin
2009-12-10 18:10 ` [Qemu-devel] [PATCH 06/17] eepro100: symbolic names for pci registers Michael S. Tsirkin
2010-01-07 11:14   ` Stefan Weil
2010-01-07 11:15     ` [Qemu-devel] [PATCH] eepro100: Fix initial value for PCI_STATUS Stefan Weil
2010-01-07 12:34       ` [Qemu-devel] " Michael S. Tsirkin
2010-01-07 15:07         ` [Qemu-devel] [RFC] API change for pci_set_word and related functions (was Re: [PATCH] eepro100: Fix initial value for PCI_STATUS) Stefan Weil
2010-01-11 18:34           ` [Qemu-devel] " Michael S. Tsirkin
2010-01-11 19:38             ` Stefan Weil [this message]
2010-01-11 19:40               ` [Qemu-devel] Re: [RFC] API change for pci_set_word and related functions Michael S. Tsirkin
2010-01-11 20:18                 ` Stefan Weil
2010-01-11 20:30                   ` Michael S. Tsirkin
2010-01-11 21:51                     ` Anthony Liguori
2010-01-11 22:10                       ` Stefan Weil
2010-01-11 23:12                         ` Anthony Liguori
2010-01-07 12:51     ` [Qemu-devel] [PATCH 06/17] eepro100: symbolic names for pci registers Michael S. Tsirkin
2010-01-07 13:41       ` Anthony Liguori
2010-01-07 13:32     ` Anthony Liguori
2010-01-07 14:26       ` Stefan Weil
2009-12-10 18:10 ` [Qemu-devel] [PATCH 07/17] piix: symbolic constants Michael S. Tsirkin
2009-12-10 18:10 ` [Qemu-devel] [PATCH 08/17] cmd646: symbolic names for pci registers Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 09/17] vmware_vga: " Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 10/17] lsi: " Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 11/17] pci: add another devsel macro Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 12/17] es1370: symbolic names for pci registers Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 13/17] wdt_i6300esb: " Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 14/17] ac97: " Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 15/17] usb-uhci: " Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 16/17] " Michael S. Tsirkin
     [not found]   ` <m3my1okxnw.fsf@neno.neno>
2009-12-12 20:34     ` [Qemu-devel] " Michael S. Tsirkin
2009-12-10 18:11 ` [Qemu-devel] [PATCH 17/17] pci: remove unused macro Michael S. Tsirkin

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=4B4B7E4D.5010101@mail.berlios.de \
    --to=weil@mail.berlios.de \
    --cc=mst@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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.