Changes in uspace/drv/audio/sb16/main.c [e941bf8:7de1988c] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/drv/audio/sb16/main.c
re941bf8 r7de1988c 49 49 50 50 static int sb_add_device(ddf_dev_t *device); 51 static int sb_get_res(const ddf_dev_t *device, uintptr_t *sb_regs, 52 size_t *sb_regs_size, uintptr_t *mpu_regs, size_t *mpu_regs_size, 53 int *irq, int *dma8, int *dma16); 51 static int sb_get_res(ddf_dev_t *device, addr_range_t **pp_sb_regs, 52 addr_range_t **pp_mpu_regs, int *irq, int *dma8, int *dma16); 54 53 static int sb_enable_interrupts(ddf_dev_t *device); 55 /*----------------------------------------------------------------------------*/ 54 56 55 static driver_ops_t sb_driver_ops = { 57 56 .dev_add = sb_add_device, 58 57 }; 59 /*----------------------------------------------------------------------------*/ 58 60 59 static driver_t sb_driver = { 61 60 .name = NAME, 62 61 .driver_ops = &sb_driver_ops 63 62 }; 64 //static ddf_dev_ops_t sb_ops = {}; 65 /*----------------------------------------------------------------------------*/ 66 /** Initializes global driver structures (NONE). 63 64 /** Initialize global driver structures (NONE). 67 65 * 68 66 * @param[in] argc Nmber of arguments in argv vector (ignored). … … 75 73 { 76 74 printf(NAME": HelenOS SB16 audio driver.\n"); 77 ddf_log_init(NAME , LVL_DEBUG2);75 ddf_log_init(NAME); 78 76 return ddf_driver_main(&sb_driver); 79 77 } … … 81 79 static void irq_handler(ddf_dev_t *dev, ipc_callid_t iid, ipc_call_t *call) 82 80 { 83 assert(dev); 84 assert(dev->driver_data); 85 sb16_interrupt(dev->driver_data); 86 } 87 88 /** Initializes a new ddf driver instance of SB16. 81 sb16_t *sb16_dev = ddf_dev_data_get(dev); 82 sb16_interrupt(sb16_dev); 83 } 84 85 /** Initialize new SB16 driver instance. 89 86 * 90 87 * @param[in] device DDF instance of the device to initialize. … … 93 90 static int sb_add_device(ddf_dev_t *device) 94 91 { 95 #define CHECK_RET_RETURN(ret, msg...) \ 96 if (ret != EOK) { \ 97 ddf_log_error(msg); \ 98 return ret; \ 99 } else (void)0 100 101 assert(device); 102 103 sb16_t *soft_state = ddf_dev_data_alloc(device, sizeof(sb16_t)); 104 int ret = soft_state ? EOK : ENOMEM; 105 CHECK_RET_RETURN(ret, "Failed to allocate sb16 structure."); 106 107 uintptr_t sb_regs = 0, mpu_regs = 0; 108 size_t sb_regs_size = 0, mpu_regs_size = 0; 109 int irq = 0, dma8 = 0, dma16 = 0; 110 111 ret = sb_get_res(device, &sb_regs, &sb_regs_size, &mpu_regs, 112 &mpu_regs_size, &irq, &dma8, &dma16); 113 CHECK_RET_RETURN(ret, "Failed to get resources: %s.", str_error(ret)); 114 92 bool handler_regd = false; 115 93 const size_t irq_cmd_count = sb16_irq_code_size(); 116 94 irq_cmd_t irq_cmds[irq_cmd_count]; 117 95 irq_pio_range_t irq_ranges[1]; 118 sb16_irq_code((void*)sb_regs, dma8, dma16, irq_cmds, irq_ranges); 96 97 sb16_t *soft_state = ddf_dev_data_alloc(device, sizeof(sb16_t)); 98 int rc = soft_state ? EOK : ENOMEM; 99 if (rc != EOK) { 100 ddf_log_error("Failed to allocate sb16 structure."); 101 goto error; 102 } 103 104 addr_range_t sb_regs; 105 addr_range_t *p_sb_regs = &sb_regs; 106 addr_range_t mpu_regs; 107 addr_range_t *p_mpu_regs = &mpu_regs; 108 int irq = 0, dma8 = 0, dma16 = 0; 109 110 rc = sb_get_res(device, &p_sb_regs, &p_mpu_regs, &irq, &dma8, &dma16); 111 if (rc != EOK) { 112 ddf_log_error("Failed to get resources: %s.", str_error(rc)); 113 goto error; 114 } 115 116 sb16_irq_code(p_sb_regs, dma8, dma16, irq_cmds, irq_ranges); 119 117 120 118 irq_code_t irq_code = { … … 125 123 }; 126 124 127 ret = register_interrupt_handler(device, irq, irq_handler, &irq_code); 128 CHECK_RET_RETURN(ret, 129 "Failed to register irq handler: %s.", str_error(ret)); 130 131 #define CHECK_RET_UNREG_DEST_RETURN(ret, msg...) \ 132 if (ret != EOK) { \ 133 ddf_log_error(msg); \ 134 unregister_interrupt_handler(device, irq); \ 135 return ret; \ 136 } else (void)0 137 138 ret = sb_enable_interrupts(device); 139 CHECK_RET_UNREG_DEST_RETURN(ret, "Failed to enable interrupts: %s.", 140 str_error(ret)); 141 142 ret = sb16_init_sb16( 143 soft_state, (void*)sb_regs, sb_regs_size, device, dma8, dma16); 144 CHECK_RET_UNREG_DEST_RETURN(ret, 145 "Failed to init sb16 driver: %s.", str_error(ret)); 146 147 ret = sb16_init_mpu(soft_state, (void*)mpu_regs, mpu_regs_size); 148 if (ret == EOK) { 125 rc = register_interrupt_handler(device, irq, irq_handler, &irq_code); 126 if (rc != EOK) { 127 ddf_log_error("Failed to register irq handler: %s.", 128 str_error(rc)); 129 goto error; 130 } 131 132 handler_regd = true; 133 134 rc = sb_enable_interrupts(device); 135 if (rc != EOK) { 136 ddf_log_error("Failed to enable interrupts: %s.", 137 str_error(rc)); 138 goto error; 139 } 140 141 rc = sb16_init_sb16(soft_state, p_sb_regs, device, dma8, dma16); 142 if (rc != EOK) { 143 ddf_log_error("Failed to init sb16 driver: %s.", 144 str_error(rc)); 145 goto error; 146 } 147 148 rc = sb16_init_mpu(soft_state, p_mpu_regs); 149 if (rc == EOK) { 149 150 ddf_fun_t *mpu_fun = 150 151 ddf_fun_create(device, fun_exposed, "midi"); 151 152 if (mpu_fun) { 152 r et= ddf_fun_bind(mpu_fun);153 if (r et!= EOK)153 rc = ddf_fun_bind(mpu_fun); 154 if (rc != EOK) 154 155 ddf_log_error( 155 156 "Failed to bind midi function: %s.", 156 str_error(r et));157 str_error(rc)); 157 158 } else { 158 159 ddf_log_error("Failed to create midi function."); 159 160 } 160 161 } else { 161 ddf_log_warning("Failed to init mpu driver: %s.", str_error(ret)); 162 ddf_log_warning("Failed to init mpu driver: %s.", 163 str_error(rc)); 162 164 } 163 165 164 166 /* MPU state does not matter */ 165 167 return EOK; 166 } 167 168 static int sb_get_res(const ddf_dev_t *device, uintptr_t *sb_regs, 169 size_t *sb_regs_size, uintptr_t *mpu_regs, size_t *mpu_regs_size, 170 int *irq, int *dma8, int *dma16) 168 error: 169 if (handler_regd) 170 unregister_interrupt_handler(device, irq); 171 return rc; 172 } 173 174 static int sb_get_res(ddf_dev_t *device, addr_range_t **pp_sb_regs, 175 addr_range_t **pp_mpu_regs, int *irq, int *dma8, int *dma16) 171 176 { 172 177 assert(device); 173 178 174 async_sess_t *parent_sess = 175 devman_parent_device_connect(EXCHANGE_SERIALIZE, device->handle, 176 IPC_FLAG_BLOCKING); 179 async_sess_t *parent_sess = devman_parent_device_connect( 180 EXCHANGE_SERIALIZE, ddf_dev_get_handle(device), IPC_FLAG_BLOCKING); 177 181 if (!parent_sess) 178 182 return ENOMEM; … … 219 223 } 220 224 221 222 225 if (hw_res.io_ranges.count == 1) { 223 if ( sb_regs)224 * sb_regs = hw_res.io_ranges.ranges[0].address;225 if ( sb_regs_size)226 * sb_regs_size = hw_res.io_ranges.ranges[0].size;226 if (pp_sb_regs && *pp_sb_regs) 227 **pp_sb_regs = hw_res.io_ranges.ranges[0]; 228 if (pp_mpu_regs) 229 *pp_mpu_regs = NULL; 227 230 } else { 228 231 const int sb = 229 232 (hw_res.io_ranges.ranges[0].size >= sizeof(sb16_regs_t)) 230 ? 1 : 0;233 ? 0 : 1; 231 234 const int mpu = 1 - sb; 232 if (sb_regs) 233 *sb_regs = hw_res.io_ranges.ranges[sb].address; 234 if (sb_regs_size) 235 *sb_regs_size = hw_res.io_ranges.ranges[sb].size; 236 if (mpu_regs) 237 *sb_regs = hw_res.io_ranges.ranges[mpu].address; 238 if (mpu_regs_size) 239 *sb_regs_size = hw_res.io_ranges.ranges[mpu].size; 235 if (pp_sb_regs && *pp_sb_regs) 236 **pp_sb_regs = hw_res.io_ranges.ranges[sb]; 237 if (pp_mpu_regs && *pp_mpu_regs) 238 **pp_mpu_regs = hw_res.io_ranges.ranges[mpu]; 240 239 } 241 240 … … 245 244 int sb_enable_interrupts(ddf_dev_t *device) 246 245 { 247 async_sess_t *parent_sess = 248 devman_parent_device_connect(EXCHANGE_SERIALIZE, device->handle, 249 IPC_FLAG_BLOCKING); 246 async_sess_t *parent_sess = devman_parent_device_connect( 247 EXCHANGE_SERIALIZE, ddf_dev_get_handle(device), IPC_FLAG_BLOCKING); 250 248 if (!parent_sess) 251 249 return ENOMEM; … … 256 254 return enabled ? EOK : EIO; 257 255 } 256 258 257 /** 259 258 * @}
Note:
See TracChangeset
for help on using the changeset viewer.