2006-11-21 16:07:11

by Ian molton

[permalink] [raw]
Subject: RFC - platform device, IRQs and SoC devices

Hi there.

Im working on some SoC type devices attached to the system bus of my ARM
devboard in an isa-like way.

The devices are small SoC (System On Chip) types, with one IRQ routed to
the half dozen (sub)devices on board the SoC.

At present, I am using a platform driver for the 'core' which handles
IRQ routing and device enumeration, and is currently passing the IRQ to
be used by the subdevices in a struct resource (along with two or three
IOMEM resources).

this, however means that the subdevice resource definitions must be
copied in order that the IRQ field can be set dynamically.

One solution would be for there to be a method by which the subdevice
can query the SoC core device for the base of its IRQ range, which would
allow the subdevice data to be declared as a constant and not copied.
This makes the declaration of the subdevices in the main driver very
neat and compact.

can this be done with a 'platform device' or is this simply not possible?

the real problem seems (to me) to be that struct resource is held as an
array. If it were a linked list, then I could hold all but the subdevice
IRQ in const data and simply 'tack on' a single dynamically created IRQ
resource to it.

I propose that a 'next' field be added to the struct resource. All
existing code could remain the same for now, and continue to work,
whilst newer device drivers could use the next-> field to taverse the
list rather than treat it as an array.

if all 'linked' entries come before 'array style' ones, then the
num_resources field would change to mean 'num_array_style_resources' and
the last 'linked' type resource would point to the head of the array.
The traversal routines would simply count the array offset from the
first 'array style' entry (with a NULL next field) or, if num_resources
is not set, assume all resources are linked, and the NULL ends the list
of resources.

This would allow for both statically allocated const arrays of struct
resource as we use now, and dynamically allocated resources, or a mix of
both for the few weird cases like my problem above.

Summary:

add struct resource *next; to struct resource.
rename num_resources as resource_array_len to indicate it only counts
the number of resources listed in an array
allow resources to be added dynamically by altering the pointer to the
firts resource and using that resources next pointer to point to the old
list head (OR) the old array head.

possible enhancements:

get_first_resource() - return first resource added, making it easy to
locate the first array type entry (if present)
remove_resource() - obvious, but perhaps not very useful.


2006-11-25 11:37:33

by Ian molton

[permalink] [raw]
Subject: Re: [Kernel-discuss] RFC - platform device, IRQs and SoC devices

Ian Molton wrote:
> Hi there.
>
> Im working on some SoC type devices attached to the system bus of my ARM
> devboard in an isa-like way.
>
> The devices are small SoC (System On Chip) types, with one IRQ routed to
> the half dozen (sub)devices on board the SoC.

I just thought of a 'third way'.

let IRQchips have their own struct irq_desc and have subdevice IRQs
start from 0.

since those IRQs can only be raised by the parent chip I think this
ought to work, and would eliminated the problem of a fixed size irq array...

2006-11-25 12:29:21

by Russell King

[permalink] [raw]
Subject: Re: [Kernel-discuss] RFC - platform device, IRQs and SoC devices

On Sat, Nov 25, 2006 at 11:37:50AM +0000, Ian Molton wrote:
> Ian Molton wrote:
> >Hi there.
> >
> >Im working on some SoC type devices attached to the system bus of my ARM
> >devboard in an isa-like way.
> >
> >The devices are small SoC (System On Chip) types, with one IRQ routed to
> >the half dozen (sub)devices on board the SoC.
>
> I just thought of a 'third way'.
>
> let IRQchips have their own struct irq_desc and have subdevice IRQs
> start from 0.
>
> since those IRQs can only be raised by the parent chip I think this
> ought to work, and would eliminated the problem of a fixed size irq array...

It's quite possible to have:

IRQ chip
0 irqchip_0
1 irqchip_0
2 irqchip_1
3 irqchip_0
4 irqchip_0
5 irqchip_1
6 irqchip_2
7 irqchip_2
8 irqchip_2
9 irqchip_1

Where do you start '0' for each irqchip? How do you split the irq_desc
array between the irqchips?

(and yes there are platforms merged which do this.)

--
Russell King
Linux kernel 2.6 ARM Linux - http://www.arm.linux.org.uk/
maintainer of:

2006-11-25 12:51:00

by Ian molton

[permalink] [raw]
Subject: Re: [Kernel-discuss] RFC - platform device, IRQs and SoC devices

Russell King wrote:
>
> It's quite possible to have:
>
> IRQ chip
> 0 irqchip_0
> 1 irqchip_0
> 2 irqchip_1
> 3 irqchip_0
> 4 irqchip_0
> 5 irqchip_1
> 6 irqchip_2
> 7 irqchip_2
> 8 irqchip_2
> 9 irqchip_1
>
> Where do you start '0' for each irqchip? How do you split the irq_desc
> array between the irqchips?

I see no reason why this couldnt continue to work 'as is' with the new
behaviour only applying to irqchips with their own non-NULL irq_desc array.

The other problem is integration with /proc, specifically the irq usage
counter.

The irq numbers in /proc wouldnt have to be 'real' they can be
synthesized from a base starting after the main system IRQs.

Im not sure how fixed the format of /proc/interrupts is, wether the IRQ
numbers are required to be sequential or not (some arent even numbers
like NMI on x86). if they dont have to be sequential then its simply a
matter of keeping a counter starting from BOARD_IRQ_END+1 and for each
IRQchip adding its individual irq numbers to it as they are displayed,
then incrementing the counter by the size of the irqdesc array for that
chip.

2006-11-25 13:02:49

by Russell King

[permalink] [raw]
Subject: Re: [Kernel-discuss] RFC - platform device, IRQs and SoC devices

On Sat, Nov 25, 2006 at 12:51:17PM +0000, Ian Molton wrote:
> Russell King wrote:
> >It's quite possible to have:
> >
> >IRQ chip
> >0 irqchip_0
> >1 irqchip_0
> >2 irqchip_1
> >3 irqchip_0
> >4 irqchip_0
> >5 irqchip_1
> >6 irqchip_2
> >7 irqchip_2
> >8 irqchip_2
> >9 irqchip_1
> >
> >Where do you start '0' for each irqchip? How do you split the irq_desc
> >array between the irqchips?
>
> I see no reason why this couldnt continue to work 'as is' with the new
> behaviour only applying to irqchips with their own non-NULL irq_desc array.

That creates a multi-class system. Not nice from the maintainability
aspect.

Nevertheless, please produce patches to demonstrate this idea in detail.

> The other problem is integration with /proc, specifically the irq usage
> counter.

There's interrupt numbers elsewhere in procfs other than /proc/interrupts -
eg, the /proc/stat "intr" line is just one example.

--
Russell King
Linux kernel 2.6 ARM Linux - http://www.arm.linux.org.uk/
maintainer of: