提交 95ef3940 编写于 作者: H Hans Verkuil 提交者: Mauro Carvalho Chehab

[media] go7007: remember boot firmware

Don't load it everytime you stop encoding. Instead remember it.
Another reason for not loading it every time is that this could
be called from within the release() file operation, which turns
out to be deadly.
Signed-off-by: NHans Verkuil <hans.verkuil@cisco.com>
Signed-off-by: NMauro Carvalho Chehab <mchehab@redhat.com>
上级 9b6ebf33
...@@ -95,34 +95,34 @@ static int go7007_load_encoder(struct go7007 *go) ...@@ -95,34 +95,34 @@ static int go7007_load_encoder(struct go7007 *go)
int fw_len, rv = 0; int fw_len, rv = 0;
u16 intr_val, intr_data; u16 intr_val, intr_data;
if (request_firmware(&fw_entry, fw_name, go->dev)) { if (go->boot_fw == NULL) {
v4l2_err(go, "unable to load firmware from file " if (request_firmware(&fw_entry, fw_name, go->dev)) {
"\"%s\"\n", fw_name); v4l2_err(go, "unable to load firmware from file \"%s\"\n", fw_name);
return -1; return -1;
} }
if (fw_entry->size < 16 || memcmp(fw_entry->data, "WISGO7007FW", 11)) { if (fw_entry->size < 16 || memcmp(fw_entry->data, "WISGO7007FW", 11)) {
v4l2_err(go, "file \"%s\" does not appear to be " v4l2_err(go, "file \"%s\" does not appear to be go7007 firmware\n", fw_name);
"go7007 firmware\n", fw_name); release_firmware(fw_entry);
release_firmware(fw_entry); return -1;
return -1; }
} fw_len = fw_entry->size - 16;
fw_len = fw_entry->size - 16; bounce = kmemdup(fw_entry->data + 16, fw_len, GFP_KERNEL);
bounce = kmemdup(fw_entry->data + 16, fw_len, GFP_KERNEL); if (bounce == NULL) {
if (bounce == NULL) { v4l2_err(go, "unable to allocate %d bytes for firmware transfer\n", fw_len);
v4l2_err(go, "unable to allocate %d bytes for " release_firmware(fw_entry);
"firmware transfer\n", fw_len); return -1;
}
release_firmware(fw_entry); release_firmware(fw_entry);
return -1; go->boot_fw_len = fw_len;
go->boot_fw = bounce;
} }
release_firmware(fw_entry);
if (go7007_interface_reset(go) < 0 || if (go7007_interface_reset(go) < 0 ||
go7007_send_firmware(go, bounce, fw_len) < 0 || go7007_send_firmware(go, go->boot_fw, go->boot_fw_len) < 0 ||
go7007_read_interrupt(go, &intr_val, &intr_data) < 0 || go7007_read_interrupt(go, &intr_val, &intr_data) < 0 ||
(intr_val & ~0x1) != 0x5a5a) { (intr_val & ~0x1) != 0x5a5a) {
v4l2_err(go, "error transferring firmware\n"); v4l2_err(go, "error transferring firmware\n");
rv = -1; rv = -1;
} }
kfree(bounce);
return rv; return rv;
} }
...@@ -675,6 +675,7 @@ void go7007_remove(struct go7007 *go) ...@@ -675,6 +675,7 @@ void go7007_remove(struct go7007 *go)
if (go->audio_enabled) if (go->audio_enabled)
go7007_snd_remove(go); go7007_snd_remove(go);
kfree(go->boot_fw);
go7007_v4l2_remove(go); go7007_v4l2_remove(go);
} }
EXPORT_SYMBOL(go7007_remove); EXPORT_SYMBOL(go7007_remove);
......
...@@ -178,6 +178,8 @@ struct go7007 { ...@@ -178,6 +178,8 @@ struct go7007 {
int channel_number; /* for multi-channel boards like Adlink PCI-MPG24 */ int channel_number; /* for multi-channel boards like Adlink PCI-MPG24 */
char name[64]; char name[64];
struct video_device *video_dev; struct video_device *video_dev;
void *boot_fw;
unsigned boot_fw_len;
struct v4l2_device v4l2_dev; struct v4l2_device v4l2_dev;
int ref_count; int ref_count;
enum { STATUS_INIT, STATUS_ONLINE, STATUS_SHUTDOWN } status; enum { STATUS_INIT, STATUS_ONLINE, STATUS_SHUTDOWN } status;
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册