linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] fpga: zynq-fpga: Replacing BIT with BIN format
@ 2015-10-20  0:01 Moritz Fischer
  2015-10-20  0:01 ` [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit Moritz Fischer
  0 siblings, 1 reply; 7+ messages in thread
From: Moritz Fischer @ 2015-10-20  0:01 UTC (permalink / raw)
  To: linux-arm-kernel

Hi all,

as discussed, here a patch that removes the byteswapping
code, leaving format conversion to userland.

However I added a crude check to bail out early if the sync word
isn't found in the firmware file, to avoid kicking the hardware
unneccesary.

This change requires people to use the appropriate Xilinx tools to
generate the (byteswapped) .bin files.

Cheers,

    Moritz

Moritz Fischer (1):
  fpga: zynq-fpga: Change fw format to handle bin instead of bit.

 drivers/fpga/zynq-fpga.c | 23 ++++++++++-------------
 1 file changed, 10 insertions(+), 13 deletions(-)

-- 
2.6.1

^ permalink raw reply	[flat|nested] 7+ messages in thread

* [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit.
  2015-10-20  0:01 [PATCH] fpga: zynq-fpga: Replacing BIT with BIN format Moritz Fischer
@ 2015-10-20  0:01 ` Moritz Fischer
  2015-10-20  5:24   ` Mike Looijmans
                     ` (2 more replies)
  0 siblings, 3 replies; 7+ messages in thread
From: Moritz Fischer @ 2015-10-20  0:01 UTC (permalink / raw)
  To: linux-arm-kernel

This gets rid of the code to strip away the header and byteswap.

Signed-off-by: Moritz Fischer <moritz.fischer@ettus.com>
---
 drivers/fpga/zynq-fpga.c | 23 ++++++++++-------------
 1 file changed, 10 insertions(+), 13 deletions(-)

diff --git a/drivers/fpga/zynq-fpga.c b/drivers/fpga/zynq-fpga.c
index 617d382..916c551 100644
--- a/drivers/fpga/zynq-fpga.c
+++ b/drivers/fpga/zynq-fpga.c
@@ -104,6 +104,8 @@
 #define INIT_POLL_TIMEOUT		2500000
 /* Delay for polling reset bits */
 #define INIT_POLL_DELAY			20
+/* Sync sequence for firmware */
+#define SYNC_SEQUENCE			"\x66\x55\x99\xAA"
 
 /* Masks for controlling stuff in SLCR */
 /* Disable all Level shifters */
@@ -301,24 +303,19 @@ static int zynq_fpga_ops_write(struct fpga_manager *mgr,
 
 	memcpy(kbuf, buf, count);
 
-	/* look for the sync word */
+	/* look for the sync sequence */
 	for (i = 0; i < count - 4; i++) {
-		if (memcmp(kbuf + i, "\xAA\x99\x55\x66", 4) == 0) {
-			dev_dbg(priv->dev, "Found swapped sync word\n");
+		if (memcmp(kbuf + i, SYNC_SEQUENCE, 4) == 0) {
+			dev_dbg(priv->dev, "Found sync sequence");
 			break;
 		}
 	}
 
-	/* remove the header, align the data on word boundary */
-	if (i != count - 4) {
-		count -= i;
-		memmove(kbuf, kbuf + i, count);
-	}
-
-	/* fixup endianness of the data */
-	for (i = 0; i < count; i += 4) {
-		u32 *p = (u32 *)&kbuf[i];
-		*p = swab32(*p);
+	/* if we detect something obviously broken, bail ... */
+	if ((count - 4) == i) {
+		dev_err(priv->dev, "No sync sequence found, invalid bitstream.");
+		err = -EINVAL;
+		goto out_free;
 	}
 
 	/* enable clock */
-- 
2.6.1

^ permalink raw reply related	[flat|nested] 7+ messages in thread

* [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit.
  2015-10-20  0:01 ` [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit Moritz Fischer
@ 2015-10-20  5:24   ` Mike Looijmans
  2015-10-20  8:33     ` Moritz Fischer
  2015-10-20  6:54   ` Mike Looijmans
  2015-10-20  6:57   ` Mike Looijmans
  2 siblings, 1 reply; 7+ messages in thread
From: Mike Looijmans @ 2015-10-20  5:24 UTC (permalink / raw)
  To: linux-arm-kernel

?On 20-10-15 02:01, Moritz Fischer wrote:
> This gets rid of the code to strip away the header and byteswap.
>
> Signed-off-by: Moritz Fischer <moritz.fischer@ettus.com>
> ---
>   drivers/fpga/zynq-fpga.c | 23 ++++++++++-------------
>   1 file changed, 10 insertions(+), 13 deletions(-)
>
> diff --git a/drivers/fpga/zynq-fpga.c b/drivers/fpga/zynq-fpga.c
> index 617d382..916c551 100644
> --- a/drivers/fpga/zynq-fpga.c
> +++ b/drivers/fpga/zynq-fpga.c
> @@ -104,6 +104,8 @@
>   #define INIT_POLL_TIMEOUT		2500000
>   /* Delay for polling reset bits */
>   #define INIT_POLL_DELAY			20
> +/* Sync sequence for firmware */
> +#define SYNC_SEQUENCE			"\x66\x55\x99\xAA"
>
>   /* Masks for controlling stuff in SLCR */
>   /* Disable all Level shifters */
> @@ -301,24 +303,19 @@ static int zynq_fpga_ops_write(struct fpga_manager *mgr,
>
>   	memcpy(kbuf, buf, count);
>
> -	/* look for the sync word */
> +	/* look for the sync sequence */
>   	for (i = 0; i < count - 4; i++) {
> -		if (memcmp(kbuf + i, "\xAA\x99\x55\x66", 4) == 0) {
> -			dev_dbg(priv->dev, "Found swapped sync word\n");
> +		if (memcmp(kbuf + i, SYNC_SEQUENCE, 4) == 0) {
> +			dev_dbg(priv->dev, "Found sync sequence");
>   			break;
>   		}
>   	}

Regarding this check, and judging from the code, I'd say that any file with a 
non word-aligned sync word is broken. So you could speed this up considerably 
by walking through the array word-by-word instread of byte-by-byte.

Checking the whole 4MB buffer from beginning to end doesn't make it really 
efficient either, if you're going to visit all that memory in case the stream 
is invalid, you might as well send it to the hardware, I wouldn't be surprised 
if that even takes less effort than going through it byte-by-byte.

I for one would rather see this check removed, the hardware handles it just 
fine and also catches more likely errors (e.g. sending a 7030 bitstream to a 
7015 chip is something that the driver cannot catch anyway, but the hardware 
detects that error just fine).

> -	/* remove the header, align the data on word boundary */
> -	if (i != count - 4) {
> -		count -= i;
> -		memmove(kbuf, kbuf + i, count);
> -	}
> -
> -	/* fixup endianness of the data */
> -	for (i = 0; i < count; i += 4) {
> -		u32 *p = (u32 *)&kbuf[i];
> -		*p = swab32(*p);
> +	/* if we detect something obviously broken, bail ... */
> +	if ((count - 4) == i) {
> +		dev_err(priv->dev, "No sync sequence found, invalid bitstream.");
> +		err = -EINVAL;
> +		goto out_free;
>   	}
>
>   	/* enable clock */
>



Kind regards,

Mike Looijmans
System Expert

TOPIC Embedded Products
Eindhovenseweg 32-C, NL-5683 KH Best
Postbus 440, NL-5680 AK Best
Telefoon: +31 (0) 499 33 69 79
Telefax: +31 (0) 499 33 69 70
E-mail: mike.looijmans at topicproducts.com
Website: www.topicproducts.com

Please consider the environment before printing this e-mail

Visit us at : Aerospace Electrical Systems Expo Europe which will be held from 17.11.2015 till 19.11.2015, Findorffstra?e 101 Bremen, Germany, Hall 5, stand number C65
http://www.aesexpo.eu

^ permalink raw reply	[flat|nested] 7+ messages in thread

* [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit.
  2015-10-20  0:01 ` [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit Moritz Fischer
  2015-10-20  5:24   ` Mike Looijmans
@ 2015-10-20  6:54   ` Mike Looijmans
  2015-10-20  6:57   ` Mike Looijmans
  2 siblings, 0 replies; 7+ messages in thread
From: Mike Looijmans @ 2015-10-20  6:54 UTC (permalink / raw)
  To: linux-arm-kernel

?On 20-10-15 02:01, Moritz Fischer wrote:
> This gets rid of the code to strip away the header and byteswap.
>
> Signed-off-by: Moritz Fischer <moritz.fischer@ettus.com>
> ---
>   drivers/fpga/zynq-fpga.c | 23 ++++++++++-------------
>   1 file changed, 10 insertions(+), 13 deletions(-)
>
> diff --git a/drivers/fpga/zynq-fpga.c b/drivers/fpga/zynq-fpga.c
> index 617d382..916c551 100644
> --- a/drivers/fpga/zynq-fpga.c
> +++ b/drivers/fpga/zynq-fpga.c
> @@ -104,6 +104,8 @@
>   #define INIT_POLL_TIMEOUT		2500000
>   /* Delay for polling reset bits */
>   #define INIT_POLL_DELAY			20
> +/* Sync sequence for firmware */
> +#define SYNC_SEQUENCE			"\x66\x55\x99\xAA"
>
>   /* Masks for controlling stuff in SLCR */
>   /* Disable all Level shifters */
> @@ -301,24 +303,19 @@ static int zynq_fpga_ops_write(struct fpga_manager *mgr,
>
>   	memcpy(kbuf, buf, count);
>
> -	/* look for the sync word */
> +	/* look for the sync sequence */
>   	for (i = 0; i < count - 4; i++) {
> -		if (memcmp(kbuf + i, "\xAA\x99\x55\x66", 4) == 0) {
> -			dev_dbg(priv->dev, "Found swapped sync word\n");
> +		if (memcmp(kbuf + i, SYNC_SEQUENCE, 4) == 0) {
> +			dev_dbg(priv->dev, "Found sync sequence");
>   			break;
>   		}
>   	}

Regarding this check, and judging from the code, I'd say that any file with a 
non word-aligned sync word is broken. So you could speed this up considerably 
by walking through the array word-by-word instread of byte-by-byte.

Checking the whole 4MB buffer from beginning to end doesn't make it really 
efficient either, if you're going to visit all that memory in case the stream 
is invalid, you might as well send it to the hardware, I wouldn't be surprised 
if that even takes less effort than going through it byte-by-byte.

I for one would rather see this check removed, the hardware handles it just 
fine and also catches more likely errors (e.g. sending a 7030 bitstream to a 
7015 chip is something that the driver cannot catch anyway, but the hardware 
detects that error just fine).

> -	/* remove the header, align the data on word boundary */
> -	if (i != count - 4) {
> -		count -= i;
> -		memmove(kbuf, kbuf + i, count);
> -	}
> -
> -	/* fixup endianness of the data */
> -	for (i = 0; i < count; i += 4) {
> -		u32 *p = (u32 *)&kbuf[i];
> -		*p = swab32(*p);
> +	/* if we detect something obviously broken, bail ... */
> +	if ((count - 4) == i) {
> +		dev_err(priv->dev, "No sync sequence found, invalid bitstream.");
> +		err = -EINVAL;
> +		goto out_free;
>   	}
>
>   	/* enable clock */
>



Kind regards,

Mike Looijmans
System Expert

TOPIC Embedded Products
Eindhovenseweg 32-C, NL-5683 KH Best
Postbus 440, NL-5680 AK Best
Telefoon: +31 (0) 499 33 69 79
Telefax: +31 (0) 499 33 69 70
E-mail: mike.looijmans at topicproducts.com
Website: www.topicproducts.com

Please consider the environment before printing this e-mail

Visit us at : Aerospace Electrical Systems Expo Europe which will be held from 17.11.2015 till 19.11.2015, Findorffstra?e 101 Bremen, Germany, Hall 5, stand number C65
http://www.aesexpo.eu

^ permalink raw reply	[flat|nested] 7+ messages in thread

* [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit.
  2015-10-20  0:01 ` [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit Moritz Fischer
  2015-10-20  5:24   ` Mike Looijmans
  2015-10-20  6:54   ` Mike Looijmans
@ 2015-10-20  6:57   ` Mike Looijmans
  2015-10-20 11:06     ` Mike Looijmans
  2 siblings, 1 reply; 7+ messages in thread
From: Mike Looijmans @ 2015-10-20  6:57 UTC (permalink / raw)
  To: linux-arm-kernel

On 20-10-15 02:01, Moritz Fischer wrote:
> This gets rid of the code to strip away the header and byteswap.
>
> Signed-off-by: Moritz Fischer <moritz.fischer@ettus.com>
> ---
>   drivers/fpga/zynq-fpga.c | 23 ++++++++++-------------
>   1 file changed, 10 insertions(+), 13 deletions(-)
>
> diff --git a/drivers/fpga/zynq-fpga.c b/drivers/fpga/zynq-fpga.c
> index 617d382..916c551 100644
> --- a/drivers/fpga/zynq-fpga.c
> +++ b/drivers/fpga/zynq-fpga.c
> @@ -104,6 +104,8 @@
>   #define INIT_POLL_TIMEOUT		2500000
>   /* Delay for polling reset bits */
>   #define INIT_POLL_DELAY			20
> +/* Sync sequence for firmware */
> +#define SYNC_SEQUENCE			"\x66\x55\x99\xAA"
>
>   /* Masks for controlling stuff in SLCR */
>   /* Disable all Level shifters */
> @@ -301,24 +303,19 @@ static int zynq_fpga_ops_write(struct fpga_manager *mgr,
>
>   	memcpy(kbuf, buf, count);
>
> -	/* look for the sync word */
> +	/* look for the sync sequence */
>   	for (i = 0; i < count - 4; i++) {
> -		if (memcmp(kbuf + i, "\xAA\x99\x55\x66", 4) == 0) {
> -			dev_dbg(priv->dev, "Found swapped sync word\n");
> +		if (memcmp(kbuf + i, SYNC_SEQUENCE, 4) == 0) {
> +			dev_dbg(priv->dev, "Found sync sequence");
>   			break;
>   		}
>   	}

Regarding this check, and judging from the code, I'd say that any file with a 
non word-aligned sync word is broken. So you could speed this up considerably 
by walking through the array word-by-word instread of byte-by-byte.

Checking the whole 4MB buffer from beginning to end doesn't make it really 
efficient either, if you're going to visit all that memory in case the stream 
is invalid, you might as well send it to the hardware, I wouldn't be surprised 
if that even takes less effort than going through it byte-by-byte.

I for one would rather see this check removed, the hardware handles it just 
fine and also catches more likely errors (e.g. sending a 7030 bitstream to a 
7015 chip is something that the driver cannot catch anyway, but the hardware 
detects that error just fine).

> -	/* remove the header, align the data on word boundary */
> -	if (i != count - 4) {
> -		count -= i;
> -		memmove(kbuf, kbuf + i, count);
> -	}
> -
> -	/* fixup endianness of the data */
> -	for (i = 0; i < count; i += 4) {
> -		u32 *p = (u32 *)&kbuf[i];
> -		*p = swab32(*p);
> +	/* if we detect something obviously broken, bail ... */
> +	if ((count - 4) == i) {
> +		dev_err(priv->dev, "No sync sequence found, invalid bitstream.");
> +		err = -EINVAL;
> +		goto out_free;
>   	}
>
>   	/* enable clock */
>

^ permalink raw reply	[flat|nested] 7+ messages in thread

* [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit.
  2015-10-20  5:24   ` Mike Looijmans
@ 2015-10-20  8:33     ` Moritz Fischer
  0 siblings, 0 replies; 7+ messages in thread
From: Moritz Fischer @ 2015-10-20  8:33 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Mike,

On Mon, Oct 19, 2015 at 10:24 PM, Mike Looijmans
<mike.looijmans@topic.nl> wrote:
> On 20-10-15 02:01, Moritz Fischer wrote:
>>
>> This gets rid of the code to strip away the header and byteswap.
>>
>> Signed-off-by: Moritz Fischer <moritz.fischer@ettus.com>
>> ---
>>   drivers/fpga/zynq-fpga.c | 23 ++++++++++-------------
>>   1 file changed, 10 insertions(+), 13 deletions(-)
>>
>> diff --git a/drivers/fpga/zynq-fpga.c b/drivers/fpga/zynq-fpga.c
>> index 617d382..916c551 100644
>> --- a/drivers/fpga/zynq-fpga.c
>> +++ b/drivers/fpga/zynq-fpga.c
>> @@ -104,6 +104,8 @@
>>   #define INIT_POLL_TIMEOUT             2500000
>>   /* Delay for polling reset bits */
>>   #define INIT_POLL_DELAY                       20
>> +/* Sync sequence for firmware */
>> +#define SYNC_SEQUENCE                  "\x66\x55\x99\xAA"
>>
>>   /* Masks for controlling stuff in SLCR */
>>   /* Disable all Level shifters */
>> @@ -301,24 +303,19 @@ static int zynq_fpga_ops_write(struct fpga_manager
>> *mgr,
>>
>>         memcpy(kbuf, buf, count);
>>
>> -       /* look for the sync word */
>> +       /* look for the sync sequence */
>>         for (i = 0; i < count - 4; i++) {
>> -               if (memcmp(kbuf + i, "\xAA\x99\x55\x66", 4) == 0) {
>> -                       dev_dbg(priv->dev, "Found swapped sync word\n");
>> +               if (memcmp(kbuf + i, SYNC_SEQUENCE, 4) == 0) {
>> +                       dev_dbg(priv->dev, "Found sync sequence");
>>                         break;
>>                 }
>>         }
>
>
> Regarding this check, and judging from the code, I'd say that any file with
> a non word-aligned sync word is broken. So you could speed this up
> considerably by walking through the array word-by-word instread of
> byte-by-byte.

True.
>
> Checking the whole 4MB buffer from beginning to end doesn't make it really
> efficient either, if you're going to visit all that memory in case the
> stream is invalid, you might as well send it to the hardware, I wouldn't be
> surprised if that even takes less effort than going through it byte-by-byte.

You raised a good point here. I was hesitant to put in the additional check,
in my tests the reloading took no noticeable time, which was good enough for my
application, so I figured rather be more 'defensive'. Probably overly defensive,
as the reloading entity would have to check for success in either case before
attempting to use the FPGA afterwards.

> I for one would rather see this check removed, the hardware handles it just
> fine and also catches more likely errors (e.g. sending a 7030 bitstream to a
> 7015 chip is something that the driver cannot catch anyway, but the hardware
> detects that error just fine).

Fair enough. I'll remove it for v2, makes the code even easier :-)

Thanks for the feedback,

Moritz

^ permalink raw reply	[flat|nested] 7+ messages in thread

* [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit.
  2015-10-20  6:57   ` Mike Looijmans
@ 2015-10-20 11:06     ` Mike Looijmans
  0 siblings, 0 replies; 7+ messages in thread
From: Mike Looijmans @ 2015-10-20 11:06 UTC (permalink / raw)
  To: linux-arm-kernel

?Sorry for having sent that out about three times, I was cleverly being fooled 
into believing the mail didn't get delivered.

I also want to apologize for adding yet another message to that list. I'm 
sorry, it won't happen again.

On 20-10-15 08:57, Mike Looijmans wrote:
...


Kind regards,

Mike Looijmans
System Expert

TOPIC Embedded Products
Eindhovenseweg 32-C, NL-5683 KH Best
Postbus 440, NL-5680 AK Best
Telefoon: +31 (0) 499 33 69 79
Telefax: +31 (0) 499 33 69 70
E-mail: mike.looijmans at topicproducts.com
Website: www.topicproducts.com

Please consider the environment before printing this e-mail

Visit us at : Aerospace Electrical Systems Expo Europe which will be held from 17.11.2015 till 19.11.2015, Findorffstrasse 101 Bremen, Germany, Hall 5, stand number C65
http://www.aesexpo.eu

^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2015-10-20 11:06 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2015-10-20  0:01 [PATCH] fpga: zynq-fpga: Replacing BIT with BIN format Moritz Fischer
2015-10-20  0:01 ` [PATCH] fpga: zynq-fpga: Change fw format to handle bin instead of bit Moritz Fischer
2015-10-20  5:24   ` Mike Looijmans
2015-10-20  8:33     ` Moritz Fischer
2015-10-20  6:54   ` Mike Looijmans
2015-10-20  6:57   ` Mike Looijmans
2015-10-20 11:06     ` Mike Looijmans

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).