Ignore:
Timestamp:
Apr 21, 2025, 7:17:25 PM (4 months ago)
Author:
David Azarewicz
Message:

Merge from uniaud32-exp branch

Location:
GPL/trunk
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • GPL/trunk

  • GPL/trunk/alsa-kernel/pci/emu10k1/io.c

    r772 r777  
    291291void snd_emu1010_fpga_write(struct snd_emu10k1 *emu, u32 reg, u32 value)
    292292{
    293         unsigned long flags;
    294 
    295         spin_lock_irqsave(&emu->emu_lock, flags);
     293#ifndef TARGET_OS2
     294        if (snd_BUG_ON(!mutex_is_locked(&emu->emu1010.lock)))
     295                return;
     296#endif
    296297        snd_emu1010_fpga_write_locked(emu, reg, value);
    297         spin_unlock_irqrestore(&emu->emu_lock, flags);
    298 }
    299 
    300 static void snd_emu1010_fpga_read_locked(struct snd_emu10k1 *emu, u32 reg, u32 *value)
     298}
     299
     300void snd_emu1010_fpga_write_lock(struct snd_emu10k1 *emu, u32 reg, u32 value)
     301{
     302        snd_emu1010_fpga_lock(emu);
     303        snd_emu1010_fpga_write_locked(emu, reg, value);
     304        snd_emu1010_fpga_unlock(emu);
     305}
     306
     307void snd_emu1010_fpga_read(struct snd_emu10k1 *emu, u32 reg, u32 *value)
    301308{
    302309        // The higest input pin is used as the designated interrupt trigger,
     
    305312        // so using this function often causes an IRQ as a side effect.
    306313        u32 mask = emu->card_capabilities->ca0108_chip ? 0x1f : 0x7f;
     314
     315#ifndef TARGET_OS2
     316        if (snd_BUG_ON(!mutex_is_locked(&emu->emu1010.lock)))
     317                return;
     318#endif
    307319        if (snd_BUG_ON(reg > 0x3f))
    308320                return;
     
    315327}
    316328
    317 void snd_emu1010_fpga_read(struct snd_emu10k1 *emu, u32 reg, u32 *value)
    318 {
    319         unsigned long flags;
    320 
    321         spin_lock_irqsave(&emu->emu_lock, flags);
    322         snd_emu1010_fpga_read_locked(emu, reg, value);
    323         spin_unlock_irqrestore(&emu->emu_lock, flags);
    324 }
    325 
    326329/* Each Destination has one and only one Source,
    327330 * but one Source can feed any number of Destinations simultaneously.
     
    329332void snd_emu1010_fpga_link_dst_src_write(struct snd_emu10k1 *emu, u32 dst, u32 src)
    330333{
    331         unsigned long flags;
    332 
    333334        if (snd_BUG_ON(dst & ~0x71f))
    334335                return;
    335336        if (snd_BUG_ON(src & ~0x71f))
    336337                return;
    337         spin_lock_irqsave(&emu->emu_lock, flags);
    338         snd_emu1010_fpga_write_locked(emu, EMU_HANA_DESTHI, dst >> 8);
    339         snd_emu1010_fpga_write_locked(emu, EMU_HANA_DESTLO, dst & 0x1f);
    340         snd_emu1010_fpga_write_locked(emu, EMU_HANA_SRCHI, src >> 8);
    341         snd_emu1010_fpga_write_locked(emu, EMU_HANA_SRCLO, src & 0x1f);
    342         spin_unlock_irqrestore(&emu->emu_lock, flags);
     338        snd_emu1010_fpga_write(emu, EMU_HANA_DESTHI, dst >> 8);
     339        snd_emu1010_fpga_write(emu, EMU_HANA_DESTLO, dst & 0x1f);
     340        snd_emu1010_fpga_write(emu, EMU_HANA_SRCHI, src >> 8);
     341        snd_emu1010_fpga_write(emu, EMU_HANA_SRCLO, src & 0x1f);
    343342}
    344343
    345344u32 snd_emu1010_fpga_link_dst_src_read(struct snd_emu10k1 *emu, u32 dst)
    346345{
    347         unsigned long flags;
    348346        u32 hi, lo;
    349347
    350348        if (snd_BUG_ON(dst & ~0x71f))
    351349                return 0;
    352         spin_lock_irqsave(&emu->emu_lock, flags);
    353         snd_emu1010_fpga_write_locked(emu, EMU_HANA_DESTHI, dst >> 8);
    354         snd_emu1010_fpga_write_locked(emu, EMU_HANA_DESTLO, dst & 0x1f);
    355         snd_emu1010_fpga_read_locked(emu, EMU_HANA_SRCHI, &hi);
    356         snd_emu1010_fpga_read_locked(emu, EMU_HANA_SRCLO, &lo);
    357         spin_unlock_irqrestore(&emu->emu_lock, flags);
     350        snd_emu1010_fpga_write(emu, EMU_HANA_DESTHI, dst >> 8);
     351        snd_emu1010_fpga_write(emu, EMU_HANA_DESTLO, dst & 0x1f);
     352        snd_emu1010_fpga_read(emu, EMU_HANA_SRCHI, &hi);
     353        snd_emu1010_fpga_read(emu, EMU_HANA_SRCLO, &lo);
    358354        return (hi << 8) | lo;
    359355}
     
    429425
    430426        snd_emu1010_fpga_write(emu, EMU_HANA_DOCK_LEDS_2, leds);
     427}
     428
     429void snd_emu1010_load_firmware_entry(struct snd_emu10k1 *emu, int dock,
     430                                     const struct firmware *fw_entry)
     431{
     432        __always_unused u16 write_post;
     433
     434        // On E-MU 1010 rev1 the FPGA is a Xilinx Spartan IIE XC2S50E.
     435        // On E-MU 0404b it is a Xilinx Spartan III XC3S50.
     436        // The wiring is as follows:
     437        // GPO7 -> FPGA input & 1K resistor -> FPGA /PGMN <- FPGA output
     438        //   In normal operation, the active low reset line is held up by
     439        //   an FPGA output, while the GPO pin performs its duty as control
     440        //   register access strobe signal. Writing the respective bit to
     441        //   EMU_HANA_FPGA_CONFIG puts the FPGA output into high-Z mode, at
     442        //   which point the GPO pin can control the reset line through the
     443        //   resistor.
     444        // GPO6 -> FPGA CCLK & FPGA input
     445        // GPO5 -> FPGA DIN (dual function)
     446
     447        // If the FPGA is already programmed, return it to programming mode
     448        snd_emu1010_fpga_write(emu, EMU_HANA_FPGA_CONFIG,
     449                               dock ? EMU_HANA_FPGA_CONFIG_AUDIODOCK :
     450                                      EMU_HANA_FPGA_CONFIG_HANA);
     451
     452        // Assert reset line for 100uS
     453        outw(0x00, emu->port + A_GPIO);
     454        write_post = inw(emu->port + A_GPIO);
     455        udelay(100);
     456        outw(0x80, emu->port + A_GPIO);
     457        write_post = inw(emu->port + A_GPIO);
     458        udelay(100);  // Allow FPGA memory to clean
     459
     460        // Upload the netlist. Keep reset line high!
     461        for (int n = 0; n < fw_entry->size; n++) {
     462                u8 value = fw_entry->data[n];
     463                for (int i = 0; i < 8; i++) {
     464                        u16 reg = 0x80;
     465                        if (value & 1)
     466                                reg |= 0x20;
     467                        value >>= 1;
     468                        outw(reg, emu->port + A_GPIO);
     469                        write_post = inw(emu->port + A_GPIO);
     470                        outw(reg | 0x40, emu->port + A_GPIO);
     471                        write_post = inw(emu->port + A_GPIO);
     472                }
     473        }
     474
     475        // After programming, set GPIO bit 4 high again.
     476        // This appears to be a config word that the rev1 Hana
     477        // firmware reads; weird things happen without this.
     478        outw(0x10, emu->port + A_GPIO);
     479        write_post = inw(emu->port + A_GPIO);
    431480}
    432481
Note: See TracChangeset for help on using the changeset viewer.