Re: [pm-wip/uart][PATCH] Serial: Avoid populating uart_list in early init phase

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Sat, Jun 26, 2010 at 9:38 PM, DebBarma, Tarun Kanti
<tarun.kanti@xxxxxx> wrote:
>
>> -----Original Message-----
>> From: linux-omap-owner@xxxxxxxxxxxxxxx [mailto:linux-omap-
>> owner@xxxxxxxxxxxxxxx] On Behalf Of Govindraj.R
>> Sent: Friday, June 25, 2010 7:12 PM
>> To: linux-omap@xxxxxxxxxxxxxxx
>> Cc: Kevin Hilman
>> Subject: [pm-wip/uart][PATCH] Serial: Avoid populating uart_list in early
>> init phase
>>
>> Leave the uart_list empty and keep the omap hwmod info
>> in a seperate uart_oh list and if board file calls
>> serial init use this uart_oh list info to fill uart_list.
>> The board file can also call just init_port to initialise
>> a single uart instance, so make init_port flexible to handle
>> individual uart instance by avoiding filling uart_list
>> in any non port_init function.
>>
>> Cc: Kevin Hilman <khilman@xxxxxxxxxxxxxxxxxxx>
>> Signed-off-by: Govindraj.R <govindraj.raja@xxxxxx>
>> ---
>> As per earlier dicussion:
>> http://www.mail-archive.com/linux-omap@xxxxxxxxxxxxxxx/msg31157.html
>>
>>  arch/arm/mach-omap2/serial.c |   60 +++++++++++++++++++++++++------------
>> ----
>>  1 files changed, 36 insertions(+), 24 deletions(-)
>>
>> diff --git a/arch/arm/mach-omap2/serial.c b/arch/arm/mach-omap2/serial.c
>> index 24b8c60..246ae02 100644
>> --- a/arch/arm/mach-omap2/serial.c
>> +++ b/arch/arm/mach-omap2/serial.c
>> @@ -97,6 +97,13 @@ struct omap_uart_state {
>>  #endif
>>  };
>>
>> +struct uart_oh {
>> +     struct list_head node;
>> +     struct omap_hwmod *oh;
>> +     int uart_num;
>> +};
>> +
>> +static LIST_HEAD(uart_oh_list);
>>  static LIST_HEAD(uart_list);
>>  static u8 num_uarts;
>>
>> @@ -593,39 +600,32 @@ static void serial_out_override(struct uart_port
>> *up, int offset, int value)
>>
>>  void __init omap_serial_early_init(void)
>>  {
>> -     int i = 0;
>> +     struct omap_hwmod *oh;
>> +     struct uart_oh *uoh;
>> +     char oh_name[MAX_UART_HWMOD_NAME_LEN];
>>
>>       do {
>> -             char oh_name[MAX_UART_HWMOD_NAME_LEN];
>> -             struct omap_hwmod *oh;
>> -             struct omap_uart_state *uart;
>> +             uoh = kzalloc(sizeof(struct uart_oh), GFP_KERNEL);
>> +             if (WARN_ON(!uoh))
>> +                     return;
>>
>>               snprintf(oh_name, MAX_UART_HWMOD_NAME_LEN,
>> -                      "uart%d", i + 1);
>> +                      "uart%d", num_uarts + 1);
>>               oh = omap_hwmod_lookup(oh_name);
>>               if (!oh)
>>                       break;
>
> [Tarun Kanti DebBarma]
> What happens to the successfully allocated memory (uoh)? Are we not supposed to free it before breaking?
>

oh is based on port instance if one instance of device is successful
we should retain
its instance rather warn only on the port instance where we failed.


> In fact, is there any problem if we do the allocation at this point?
> +               uoh = kzalloc(sizeof(struct uart_oh), GFP_KERNEL);
> +               if (WARN_ON(!uoh))
> +                       return;
>
> This would mean that we allocate and do the rest of initialization only when omap_hwmod_lookup() is >successful.
>
>> -
>> -             uart = kzalloc(sizeof(struct omap_uart_state), GFP_KERNEL);
>> -             if (WARN_ON(!uart))
>> -                     return;
>> -
>> -             uart->oh = oh;
>> -             uart->num = i++;
>> -             list_add_tail(&uart->node, &uart_list);
>> -             num_uarts++;
>> -
>>               /*
>>                * NOTE: omap_hwmod_init() has not yet been called,
>> -              *       so no hwmod functions will work yet.
>> -              */
>> -
>> -             /*
>> +              * so no hwmod functions will work yet.
>>                * During UART early init, device need to be probed
>>                * to determine SoC specific init before omap_device
>> -              * is ready.  Therefore, don't allow idle here
>> +              * is ready. Therefore, don't allow idle here
>>                */
>> -             uart->oh->flags |= HWMOD_INIT_NO_IDLE;
>> +             oh->flags |= HWMOD_INIT_NO_IDLE;
>> +             uoh->oh = oh;
>> +             uoh->uart_num = num_uarts;
>> +             list_add_tail(&uoh->node, &uart_oh_list);
>> +             num_uarts++;
>>       } while (1);
>>  }
>>
>> @@ -645,6 +645,7 @@ void __init omap_serial_init_port(int port)
>>       struct omap_uart_state *uart;
>>       struct omap_hwmod *oh;
>>       struct omap_device *od;
>> +     struct uart_oh *uoh;
>>       void *pdata = NULL;
>>       u32 pdata_size = 0;
>>       char *name;
>> @@ -663,6 +664,17 @@ void __init omap_serial_init_port(int port)
>>       if (WARN_ON(port >= num_uarts))
>>               return;
> [Tarun Kanti DebBarma]
> I am not sure if this check is needed at all since this is called for all valid ports in uart_oh_list. In other >words validation of port number has happened already while creating the uart_oh_list.
>
>>
>> +     uart = kzalloc(sizeof(struct omap_uart_state), GFP_KERNEL);
>> +     if (WARN_ON(!uart))
>> +             return;
>> +
>> +     uart->num = port;
>> +     list_add_tail(&uart->node, &uart_list);
>> +     list_for_each_entry(uoh, &uart_oh_list, node)
>> +             if (port == uoh->uart_num)
>> +                     break;
>> +
> [Tarun Kanti DebBarma]
> BTW, why can't we pass (uoh) to this function instead of port number? In that case we would any way get >the port number using uoh->uart_num as well as avoid the above loop for parsing the uart_oh_list for >identifying the respective uoh just for making the below assignment.
>
>> +     uart->oh = uoh->oh;
>>       list_for_each_entry(uart, &uart_list, node)
>>               if (port == uart->num)
>>                       break;
>> @@ -781,8 +793,8 @@ void __init omap_serial_init_port(int port)
>>   */
>>  void __init omap_serial_init(void)
>>  {
>> -     struct omap_uart_state *uart;
>> +     struct uart_oh *uoh;
>>
>> -     list_for_each_entry(uart, &uart_list, node)
>> -             omap_serial_init_port(uart->num);
>> +     list_for_each_entry(uoh, &uart_oh_list, node)
>> +             omap_serial_init_port(uoh->uart_num);
> [Tarun Kanti DebBarma]
> As mentioned above, can we pass (uoh) directly instead of (uoh->uart_num) ?

the reason for not passing uoh to init_port is because init_port can
be called directly to initialize any single
instance of the port with a port number based on the board used.

Regards,
Govindraj.R
--
To unsubscribe from this list: send the line "unsubscribe linux-omap" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[Index of Archives]     [Linux Arm (vger)]     [ARM Kernel]     [ARM MSM]     [Linux Tegra]     [Linux WPAN Networking]     [Linux Wireless Networking]     [Maemo Users]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite Trails]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux