diff options
| author | Giuliano Pochini <pochini@shiny.it> | 2010-02-14 12:15:51 -0500 |
|---|---|---|
| committer | Takashi Iwai <tiwai@suse.de> | 2010-02-15 04:38:10 -0500 |
| commit | 4f8ada444cc7a7ea70cdc81f098b34c5f1f2df41 (patch) | |
| tree | ded4e81a8e822ee43bdcaab71084c7b0bd58701f | |
| parent | 19b50063780953563e3c3a2867c39aad7b9e64cf (diff) | |
ALSA: Echoaudio - Add firmware cache #2
This patch implements a simple cache for the firmware files when CONFIG_PM is defined.
This patch changes get_firmware(), free_firmware() and adds
free_firmware_cache(). The first two functions implement a very
simple cache and the latter is used to actually release all the stored
firmwares when the module is unloaded.
When CONFIG_PM is not enabled those functions act as before, that is
free_firmware() releases the firmware immediately and
free_firmware_cache() does nothing.
Signed-off-by: Giuliano Pochini <pochini@shiny.it>
Signed-off-by: Takashi Iwai <tiwai@suse.de>
| -rw-r--r-- | sound/pci/echoaudio/echoaudio.c | 42 | ||||
| -rw-r--r-- | sound/pci/echoaudio/echoaudio.h | 3 |
2 files changed, 41 insertions, 4 deletions
diff --git a/sound/pci/echoaudio/echoaudio.c b/sound/pci/echoaudio/echoaudio.c index 78fc2637bfa6..79dde9592847 100644 --- a/sound/pci/echoaudio/echoaudio.c +++ b/sound/pci/echoaudio/echoaudio.c | |||
| @@ -43,12 +43,24 @@ static int get_firmware(const struct firmware **fw_entry, | |||
| 43 | { | 43 | { |
| 44 | int err; | 44 | int err; |
| 45 | char name[30]; | 45 | char name[30]; |
| 46 | const struct firmware *frm = &card_fw[fw_index]; | ||
| 47 | 46 | ||
| 48 | DE_ACT(("firmware requested: %s\n", frm->data)); | 47 | #ifdef CONFIG_PM |
| 49 | snprintf(name, sizeof(name), "ea/%s", frm->data); | 48 | if (chip->fw_cache[fw_index]) { |
| 50 | if ((err = request_firmware(fw_entry, name, pci_device(chip))) < 0) | 49 | DE_ACT(("firmware requested: %s is cached\n", card_fw[fw_index].data)); |
| 50 | *fw_entry = chip->fw_cache[fw_index]; | ||
| 51 | return 0; | ||
| 52 | } | ||
| 53 | #endif | ||
| 54 | |||
| 55 | DE_ACT(("firmware requested: %s\n", card_fw[fw_index].data)); | ||
| 56 | snprintf(name, sizeof(name), "ea/%s", card_fw[fw_index].data); | ||
| 57 | err = request_firmware(fw_entry, name, pci_device(chip)); | ||
| 58 | if (err < 0) | ||
| 51 | snd_printk(KERN_ERR "get_firmware(): Firmware not available (%d)\n", err); | 59 | snd_printk(KERN_ERR "get_firmware(): Firmware not available (%d)\n", err); |
| 60 | #ifdef CONFIG_PM | ||
| 61 | else | ||
| 62 | chip->fw_cache[fw_index] = *fw_entry; | ||
| 63 | #endif | ||
| 52 | return err; | 64 | return err; |
| 53 | } | 65 | } |
| 54 | 66 | ||
| @@ -56,8 +68,29 @@ static int get_firmware(const struct firmware **fw_entry, | |||
| 56 | 68 | ||
| 57 | static void free_firmware(const struct firmware *fw_entry) | 69 | static void free_firmware(const struct firmware *fw_entry) |
| 58 | { | 70 | { |
| 71 | #ifdef CONFIG_PM | ||
| 72 | DE_ACT(("firmware not released (kept in cache)\n")); | ||
| 73 | #else | ||
| 59 | release_firmware(fw_entry); | 74 | release_firmware(fw_entry); |
| 60 | DE_ACT(("firmware released\n")); | 75 | DE_ACT(("firmware released\n")); |
| 76 | #endif | ||
| 77 | } | ||
| 78 | |||
| 79 | |||
| 80 | |||
| 81 | static void free_firmware_cache(struct echoaudio *chip) | ||
| 82 | { | ||
| 83 | #ifdef CONFIG_PM | ||
| 84 | int i; | ||
| 85 | |||
| 86 | for (i = 0; i < 8 ; i++) | ||
| 87 | if (chip->fw_cache[i]) { | ||
| 88 | release_firmware(chip->fw_cache[i]); | ||
| 89 | DE_ACT(("release_firmware(%d)\n", i)); | ||
| 90 | } | ||
| 91 | |||
| 92 | DE_ACT(("firmware_cache released\n")); | ||
| 93 | #endif | ||
| 61 | } | 94 | } |
| 62 | 95 | ||
| 63 | 96 | ||
| @@ -1880,6 +1913,7 @@ static int snd_echo_free(struct echoaudio *chip) | |||
| 1880 | pci_disable_device(chip->pci); | 1913 | pci_disable_device(chip->pci); |
| 1881 | 1914 | ||
| 1882 | /* release chip data */ | 1915 | /* release chip data */ |
| 1916 | free_firmware_cache(chip); | ||
| 1883 | kfree(chip); | 1917 | kfree(chip); |
| 1884 | DE_INIT(("Chip freed.\n")); | 1918 | DE_INIT(("Chip freed.\n")); |
| 1885 | return 0; | 1919 | return 0; |
diff --git a/sound/pci/echoaudio/echoaudio.h b/sound/pci/echoaudio/echoaudio.h index be76ef3b829a..a84c0d15cc50 100644 --- a/sound/pci/echoaudio/echoaudio.h +++ b/sound/pci/echoaudio/echoaudio.h | |||
| @@ -449,6 +449,9 @@ struct echoaudio { | |||
| 449 | volatile u32 __iomem *dsp_registers; /* DSP's register base */ | 449 | volatile u32 __iomem *dsp_registers; /* DSP's register base */ |
| 450 | u32 active_mask; /* Chs. active mask or | 450 | u32 active_mask; /* Chs. active mask or |
| 451 | * punks out */ | 451 | * punks out */ |
| 452 | #ifdef CONFIG_PM | ||
| 453 | const struct firmware *fw_cache[8]; /* Cached firmwares */ | ||
| 454 | #endif | ||
| 452 | 455 | ||
| 453 | #ifdef ECHOCARD_HAS_MIDI | 456 | #ifdef ECHOCARD_HAS_MIDI |
| 454 | u16 mtc_state; /* State for MIDI input parsing state machine */ | 457 | u16 mtc_state; /* State for MIDI input parsing state machine */ |
