1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * FPGA Manager Driver for Altera SOCFPGA 4 * 5 * Copyright (C) 2013-2015 Altera Corporation 6 */ 7 #include <linux/completion.h> 8 #include <linux/delay.h> 9 #include <linux/fpga/fpga-mgr.h> 10 #include <linux/interrupt.h> 11 #include <linux/io.h> 12 #include <linux/module.h> 13 #include <linux/of_address.h> 14 #include <linux/of_irq.h> 15 #include <linux/pm.h> 16 17 /* Register offsets */ 18 #define SOCFPGA_FPGMGR_STAT_OFST 0x0 19 #define SOCFPGA_FPGMGR_CTL_OFST 0x4 20 #define SOCFPGA_FPGMGR_DCLKCNT_OFST 0x8 21 #define SOCFPGA_FPGMGR_DCLKSTAT_OFST 0xc 22 #define SOCFPGA_FPGMGR_GPIO_INTEN_OFST 0x830 23 #define SOCFPGA_FPGMGR_GPIO_INTMSK_OFST 0x834 24 #define SOCFPGA_FPGMGR_GPIO_INTTYPE_LEVEL_OFST 0x838 25 #define SOCFPGA_FPGMGR_GPIO_INT_POL_OFST 0x83c 26 #define SOCFPGA_FPGMGR_GPIO_INTSTAT_OFST 0x840 27 #define SOCFPGA_FPGMGR_GPIO_RAW_INTSTAT_OFST 0x844 28 #define SOCFPGA_FPGMGR_GPIO_PORTA_EOI_OFST 0x84c 29 #define SOCFPGA_FPGMGR_GPIO_EXT_PORTA_OFST 0x850 30 31 /* Register bit defines */ 32 /* SOCFPGA_FPGMGR_STAT register mode field values */ 33 #define SOCFPGA_FPGMGR_STAT_POWER_UP 0x0 /*ramping*/ 34 #define SOCFPGA_FPGMGR_STAT_RESET 0x1 35 #define SOCFPGA_FPGMGR_STAT_CFG 0x2 36 #define SOCFPGA_FPGMGR_STAT_INIT 0x3 37 #define SOCFPGA_FPGMGR_STAT_USER_MODE 0x4 38 #define SOCFPGA_FPGMGR_STAT_UNKNOWN 0x5 39 #define SOCFPGA_FPGMGR_STAT_STATE_MASK 0x7 40 /* This is a flag value that doesn't really happen in this register field */ 41 #define SOCFPGA_FPGMGR_STAT_POWER_OFF 0x0 42 43 #define MSEL_PP16_FAST_NOAES_NODC 0x0 44 #define MSEL_PP16_FAST_AES_NODC 0x1 45 #define MSEL_PP16_FAST_AESOPT_DC 0x2 46 #define MSEL_PP16_SLOW_NOAES_NODC 0x4 47 #define MSEL_PP16_SLOW_AES_NODC 0x5 48 #define MSEL_PP16_SLOW_AESOPT_DC 0x6 49 #define MSEL_PP32_FAST_NOAES_NODC 0x8 50 #define MSEL_PP32_FAST_AES_NODC 0x9 51 #define MSEL_PP32_FAST_AESOPT_DC 0xa 52 #define MSEL_PP32_SLOW_NOAES_NODC 0xc 53 #define MSEL_PP32_SLOW_AES_NODC 0xd 54 #define MSEL_PP32_SLOW_AESOPT_DC 0xe 55 #define SOCFPGA_FPGMGR_STAT_MSEL_MASK 0x000000f8 56 #define SOCFPGA_FPGMGR_STAT_MSEL_SHIFT 3 57 58 /* SOCFPGA_FPGMGR_CTL register */ 59 #define SOCFPGA_FPGMGR_CTL_EN 0x00000001 60 #define SOCFPGA_FPGMGR_CTL_NCE 0x00000002 61 #define SOCFPGA_FPGMGR_CTL_NCFGPULL 0x00000004 62 63 #define CDRATIO_X1 0x00000000 64 #define CDRATIO_X2 0x00000040 65 #define CDRATIO_X4 0x00000080 66 #define CDRATIO_X8 0x000000c0 67 #define SOCFPGA_FPGMGR_CTL_CDRATIO_MASK 0x000000c0 68 69 #define SOCFPGA_FPGMGR_CTL_AXICFGEN 0x00000100 70 71 #define CFGWDTH_16 0x00000000 72 #define CFGWDTH_32 0x00000200 73 #define SOCFPGA_FPGMGR_CTL_CFGWDTH_MASK 0x00000200 74 75 /* SOCFPGA_FPGMGR_DCLKSTAT register */ 76 #define SOCFPGA_FPGMGR_DCLKSTAT_DCNTDONE_E_DONE 0x1 77 78 /* SOCFPGA_FPGMGR_GPIO_* registers share the same bit positions */ 79 #define SOCFPGA_FPGMGR_MON_NSTATUS 0x0001 80 #define SOCFPGA_FPGMGR_MON_CONF_DONE 0x0002 81 #define SOCFPGA_FPGMGR_MON_INIT_DONE 0x0004 82 #define SOCFPGA_FPGMGR_MON_CRC_ERROR 0x0008 83 #define SOCFPGA_FPGMGR_MON_CVP_CONF_DONE 0x0010 84 #define SOCFPGA_FPGMGR_MON_PR_READY 0x0020 85 #define SOCFPGA_FPGMGR_MON_PR_ERROR 0x0040 86 #define SOCFPGA_FPGMGR_MON_PR_DONE 0x0080 87 #define SOCFPGA_FPGMGR_MON_NCONFIG_PIN 0x0100 88 #define SOCFPGA_FPGMGR_MON_NSTATUS_PIN 0x0200 89 #define SOCFPGA_FPGMGR_MON_CONF_DONE_PIN 0x0400 90 #define SOCFPGA_FPGMGR_MON_FPGA_POWER_ON 0x0800 91 #define SOCFPGA_FPGMGR_MON_STATUS_MASK 0x0fff 92 93 #define SOCFPGA_FPGMGR_NUM_SUPPLIES 3 94 #define SOCFPGA_RESUME_TIMEOUT 3 95 96 /* In power-up order. Reverse for power-down. */ 97 static const char *supply_names[SOCFPGA_FPGMGR_NUM_SUPPLIES] __maybe_unused = { 98 "FPGA-1.5V", 99 "FPGA-1.1V", 100 "FPGA-2.5V", 101 }; 102 103 struct socfpga_fpga_priv { 104 void __iomem *fpga_base_addr; 105 void __iomem *fpga_data_addr; 106 struct completion status_complete; 107 int irq; 108 }; 109 110 struct cfgmgr_mode { 111 /* Values to set in the CTRL register */ 112 u32 ctrl; 113 114 /* flag that this table entry is a valid mode */ 115 bool valid; 116 }; 117 118 /* For SOCFPGA_FPGMGR_STAT_MSEL field */ 119 static struct cfgmgr_mode cfgmgr_modes[] = { 120 [MSEL_PP16_FAST_NOAES_NODC] = { CFGWDTH_16 | CDRATIO_X1, 1 }, 121 [MSEL_PP16_FAST_AES_NODC] = { CFGWDTH_16 | CDRATIO_X2, 1 }, 122 [MSEL_PP16_FAST_AESOPT_DC] = { CFGWDTH_16 | CDRATIO_X4, 1 }, 123 [MSEL_PP16_SLOW_NOAES_NODC] = { CFGWDTH_16 | CDRATIO_X1, 1 }, 124 [MSEL_PP16_SLOW_AES_NODC] = { CFGWDTH_16 | CDRATIO_X2, 1 }, 125 [MSEL_PP16_SLOW_AESOPT_DC] = { CFGWDTH_16 | CDRATIO_X4, 1 }, 126 [MSEL_PP32_FAST_NOAES_NODC] = { CFGWDTH_32 | CDRATIO_X1, 1 }, 127 [MSEL_PP32_FAST_AES_NODC] = { CFGWDTH_32 | CDRATIO_X4, 1 }, 128 [MSEL_PP32_FAST_AESOPT_DC] = { CFGWDTH_32 | CDRATIO_X8, 1 }, 129 [MSEL_PP32_SLOW_NOAES_NODC] = { CFGWDTH_32 | CDRATIO_X1, 1 }, 130 [MSEL_PP32_SLOW_AES_NODC] = { CFGWDTH_32 | CDRATIO_X4, 1 }, 131 [MSEL_PP32_SLOW_AESOPT_DC] = { CFGWDTH_32 | CDRATIO_X8, 1 }, 132 }; 133 134 static u32 socfpga_fpga_readl(struct socfpga_fpga_priv *priv, u32 reg_offset) 135 { 136 return readl(priv->fpga_base_addr + reg_offset); 137 } 138 139 static void socfpga_fpga_writel(struct socfpga_fpga_priv *priv, u32 reg_offset, 140 u32 value) 141 { 142 writel(value, priv->fpga_base_addr + reg_offset); 143 } 144 145 static u32 socfpga_fpga_raw_readl(struct socfpga_fpga_priv *priv, 146 u32 reg_offset) 147 { 148 return __raw_readl(priv->fpga_base_addr + reg_offset); 149 } 150 151 static void socfpga_fpga_raw_writel(struct socfpga_fpga_priv *priv, 152 u32 reg_offset, u32 value) 153 { 154 __raw_writel(value, priv->fpga_base_addr + reg_offset); 155 } 156 157 static void socfpga_fpga_data_writel(struct socfpga_fpga_priv *priv, u32 value) 158 { 159 writel(value, priv->fpga_data_addr); 160 } 161 162 static inline void socfpga_fpga_set_bitsl(struct socfpga_fpga_priv *priv, 163 u32 offset, u32 bits) 164 { 165 u32 val; 166 167 val = socfpga_fpga_readl(priv, offset); 168 val |= bits; 169 socfpga_fpga_writel(priv, offset, val); 170 } 171 172 static inline void socfpga_fpga_clr_bitsl(struct socfpga_fpga_priv *priv, 173 u32 offset, u32 bits) 174 { 175 u32 val; 176 177 val = socfpga_fpga_readl(priv, offset); 178 val &= ~bits; 179 socfpga_fpga_writel(priv, offset, val); 180 } 181 182 static u32 socfpga_fpga_mon_status_get(struct socfpga_fpga_priv *priv) 183 { 184 return socfpga_fpga_readl(priv, SOCFPGA_FPGMGR_GPIO_EXT_PORTA_OFST) & 185 SOCFPGA_FPGMGR_MON_STATUS_MASK; 186 } 187 188 static u32 socfpga_fpga_state_get(struct socfpga_fpga_priv *priv) 189 { 190 u32 status = socfpga_fpga_mon_status_get(priv); 191 192 if ((status & SOCFPGA_FPGMGR_MON_FPGA_POWER_ON) == 0) 193 return SOCFPGA_FPGMGR_STAT_POWER_OFF; 194 195 return socfpga_fpga_readl(priv, SOCFPGA_FPGMGR_STAT_OFST) & 196 SOCFPGA_FPGMGR_STAT_STATE_MASK; 197 } 198 199 static void socfpga_fpga_clear_done_status(struct socfpga_fpga_priv *priv) 200 { 201 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_DCLKSTAT_OFST, 202 SOCFPGA_FPGMGR_DCLKSTAT_DCNTDONE_E_DONE); 203 } 204 205 /* 206 * Set the DCLKCNT, wait for DCLKSTAT to report the count completed, and clear 207 * the complete status. 208 */ 209 static int socfpga_fpga_dclk_set_and_wait_clear(struct socfpga_fpga_priv *priv, 210 u32 count) 211 { 212 int timeout = 2; 213 u32 done; 214 215 /* Clear any existing DONE status. */ 216 if (socfpga_fpga_readl(priv, SOCFPGA_FPGMGR_DCLKSTAT_OFST)) 217 socfpga_fpga_clear_done_status(priv); 218 219 /* Issue the DCLK count. */ 220 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_DCLKCNT_OFST, count); 221 222 /* Poll DCLKSTAT to see if it completed in the timeout period. */ 223 do { 224 done = socfpga_fpga_readl(priv, SOCFPGA_FPGMGR_DCLKSTAT_OFST); 225 if (done == SOCFPGA_FPGMGR_DCLKSTAT_DCNTDONE_E_DONE) { 226 socfpga_fpga_clear_done_status(priv); 227 return 0; 228 } 229 udelay(1); 230 } while (timeout--); 231 232 return -ETIMEDOUT; 233 } 234 235 static int socfpga_fpga_wait_for_state(struct socfpga_fpga_priv *priv, 236 u32 state) 237 { 238 int timeout = 2; 239 240 /* 241 * HW doesn't support an interrupt for changes in state, so poll to see 242 * if it matches the requested state within the timeout period. 243 */ 244 do { 245 if ((socfpga_fpga_state_get(priv) & state) != 0) 246 return 0; 247 msleep(20); 248 } while (timeout--); 249 250 return -ETIMEDOUT; 251 } 252 253 static void socfpga_fpga_enable_irqs(struct socfpga_fpga_priv *priv, u32 irqs) 254 { 255 /* set irqs to level sensitive */ 256 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_GPIO_INTTYPE_LEVEL_OFST, 0); 257 258 /* set interrupt polarity */ 259 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_GPIO_INT_POL_OFST, irqs); 260 261 /* clear irqs */ 262 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_GPIO_PORTA_EOI_OFST, irqs); 263 264 /* unmask interrupts */ 265 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_GPIO_INTMSK_OFST, 0); 266 267 /* enable interrupts */ 268 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_GPIO_INTEN_OFST, irqs); 269 } 270 271 static void socfpga_fpga_disable_irqs(struct socfpga_fpga_priv *priv) 272 { 273 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_GPIO_INTEN_OFST, 0); 274 } 275 276 static irqreturn_t socfpga_fpga_isr(int irq, void *dev_id) 277 { 278 struct socfpga_fpga_priv *priv = dev_id; 279 u32 irqs, st; 280 bool conf_done, nstatus; 281 282 /* clear irqs */ 283 irqs = socfpga_fpga_raw_readl(priv, SOCFPGA_FPGMGR_GPIO_INTSTAT_OFST); 284 285 socfpga_fpga_raw_writel(priv, SOCFPGA_FPGMGR_GPIO_PORTA_EOI_OFST, irqs); 286 287 st = socfpga_fpga_raw_readl(priv, SOCFPGA_FPGMGR_GPIO_EXT_PORTA_OFST); 288 conf_done = (st & SOCFPGA_FPGMGR_MON_CONF_DONE) != 0; 289 nstatus = (st & SOCFPGA_FPGMGR_MON_NSTATUS) != 0; 290 291 /* success */ 292 if (conf_done && nstatus) { 293 /* disable irqs */ 294 socfpga_fpga_raw_writel(priv, 295 SOCFPGA_FPGMGR_GPIO_INTEN_OFST, 0); 296 complete(&priv->status_complete); 297 } 298 299 return IRQ_HANDLED; 300 } 301 302 static int socfpga_fpga_wait_for_config_done(struct socfpga_fpga_priv *priv) 303 { 304 int timeout, ret = 0; 305 306 socfpga_fpga_disable_irqs(priv); 307 init_completion(&priv->status_complete); 308 socfpga_fpga_enable_irqs(priv, SOCFPGA_FPGMGR_MON_CONF_DONE); 309 310 timeout = wait_for_completion_interruptible_timeout( 311 &priv->status_complete, 312 msecs_to_jiffies(10)); 313 if (timeout == 0) 314 ret = -ETIMEDOUT; 315 316 socfpga_fpga_disable_irqs(priv); 317 return ret; 318 } 319 320 static int socfpga_fpga_cfg_mode_get(struct socfpga_fpga_priv *priv) 321 { 322 u32 msel; 323 324 msel = socfpga_fpga_readl(priv, SOCFPGA_FPGMGR_STAT_OFST); 325 msel &= SOCFPGA_FPGMGR_STAT_MSEL_MASK; 326 msel >>= SOCFPGA_FPGMGR_STAT_MSEL_SHIFT; 327 328 /* Check that this MSEL setting is supported */ 329 if ((msel >= ARRAY_SIZE(cfgmgr_modes)) || !cfgmgr_modes[msel].valid) 330 return -EINVAL; 331 332 return msel; 333 } 334 335 static int socfpga_fpga_cfg_mode_set(struct socfpga_fpga_priv *priv) 336 { 337 u32 ctrl_reg; 338 int mode; 339 340 /* get value from MSEL pins */ 341 mode = socfpga_fpga_cfg_mode_get(priv); 342 if (mode < 0) 343 return mode; 344 345 /* Adjust CTRL for the CDRATIO */ 346 ctrl_reg = socfpga_fpga_readl(priv, SOCFPGA_FPGMGR_CTL_OFST); 347 ctrl_reg &= ~SOCFPGA_FPGMGR_CTL_CDRATIO_MASK; 348 ctrl_reg &= ~SOCFPGA_FPGMGR_CTL_CFGWDTH_MASK; 349 ctrl_reg |= cfgmgr_modes[mode].ctrl; 350 351 /* Set NCE to 0. */ 352 ctrl_reg &= ~SOCFPGA_FPGMGR_CTL_NCE; 353 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_CTL_OFST, ctrl_reg); 354 355 return 0; 356 } 357 358 static int socfpga_fpga_reset(struct fpga_manager *mgr) 359 { 360 struct socfpga_fpga_priv *priv = mgr->priv; 361 u32 ctrl_reg, status; 362 int ret; 363 364 /* 365 * Step 1: 366 * - Set CTRL.CFGWDTH, CTRL.CDRATIO to match cfg mode 367 * - Set CTRL.NCE to 0 368 */ 369 ret = socfpga_fpga_cfg_mode_set(priv); 370 if (ret) 371 return ret; 372 373 /* Step 2: Set CTRL.EN to 1 */ 374 socfpga_fpga_set_bitsl(priv, SOCFPGA_FPGMGR_CTL_OFST, 375 SOCFPGA_FPGMGR_CTL_EN); 376 377 /* Step 3: Set CTRL.NCONFIGPULL to 1 to put FPGA in reset */ 378 ctrl_reg = socfpga_fpga_readl(priv, SOCFPGA_FPGMGR_CTL_OFST); 379 ctrl_reg |= SOCFPGA_FPGMGR_CTL_NCFGPULL; 380 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_CTL_OFST, ctrl_reg); 381 382 /* Step 4: Wait for STATUS.MODE to report FPGA is in reset phase */ 383 status = socfpga_fpga_wait_for_state(priv, SOCFPGA_FPGMGR_STAT_RESET); 384 385 /* Step 5: Set CONTROL.NCONFIGPULL to 0 to release FPGA from reset */ 386 ctrl_reg &= ~SOCFPGA_FPGMGR_CTL_NCFGPULL; 387 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_CTL_OFST, ctrl_reg); 388 389 /* Timeout waiting for reset */ 390 if (status) 391 return -ETIMEDOUT; 392 393 return 0; 394 } 395 396 /* 397 * Prepare the FPGA to receive the configuration data. 398 */ 399 static int socfpga_fpga_ops_configure_init(struct fpga_manager *mgr, 400 struct fpga_image_info *info, 401 const char *buf, size_t count) 402 { 403 struct socfpga_fpga_priv *priv = mgr->priv; 404 int ret; 405 406 if (info->flags & FPGA_MGR_PARTIAL_RECONFIG) { 407 dev_err(&mgr->dev, "Partial reconfiguration not supported.\n"); 408 return -EINVAL; 409 } 410 /* Steps 1 - 5: Reset the FPGA */ 411 ret = socfpga_fpga_reset(mgr); 412 if (ret) 413 return ret; 414 415 /* Step 6: Wait for FPGA to enter configuration phase */ 416 if (socfpga_fpga_wait_for_state(priv, SOCFPGA_FPGMGR_STAT_CFG)) 417 return -ETIMEDOUT; 418 419 /* Step 7: Clear nSTATUS interrupt */ 420 socfpga_fpga_writel(priv, SOCFPGA_FPGMGR_GPIO_PORTA_EOI_OFST, 421 SOCFPGA_FPGMGR_MON_NSTATUS); 422 423 /* Step 8: Set CTRL.AXICFGEN to 1 to enable transfer of config data */ 424 socfpga_fpga_set_bitsl(priv, SOCFPGA_FPGMGR_CTL_OFST, 425 SOCFPGA_FPGMGR_CTL_AXICFGEN); 426 427 return 0; 428 } 429 430 /* 431 * Step 9: write data to the FPGA data register 432 */ 433 static int socfpga_fpga_ops_configure_write(struct fpga_manager *mgr, 434 const char *buf, size_t count) 435 { 436 struct socfpga_fpga_priv *priv = mgr->priv; 437 u32 *buffer_32 = (u32 *)buf; 438 size_t i = 0; 439 440 if (count <= 0) 441 return -EINVAL; 442 443 /* Write out the complete 32-bit chunks. */ 444 while (count >= sizeof(u32)) { 445 socfpga_fpga_data_writel(priv, buffer_32[i++]); 446 count -= sizeof(u32); 447 } 448 449 /* Write out remaining non 32-bit chunks. */ 450 switch (count) { 451 case 3: 452 socfpga_fpga_data_writel(priv, buffer_32[i++] & 0x00ffffff); 453 break; 454 case 2: 455 socfpga_fpga_data_writel(priv, buffer_32[i++] & 0x0000ffff); 456 break; 457 case 1: 458 socfpga_fpga_data_writel(priv, buffer_32[i++] & 0x000000ff); 459 break; 460 case 0: 461 break; 462 default: 463 /* This will never happen. */ 464 return -EFAULT; 465 } 466 467 return 0; 468 } 469 470 static int socfpga_fpga_ops_configure_complete(struct fpga_manager *mgr, 471 struct fpga_image_info *info) 472 { 473 struct socfpga_fpga_priv *priv = mgr->priv; 474 u32 status; 475 476 /* 477 * Step 10: 478 * - Observe CONF_DONE and nSTATUS (active low) 479 * - if CONF_DONE = 1 and nSTATUS = 1, configuration was successful 480 * - if CONF_DONE = 0 and nSTATUS = 0, configuration failed 481 */ 482 status = socfpga_fpga_wait_for_config_done(priv); 483 if (status) 484 return status; 485 486 /* Step 11: Clear CTRL.AXICFGEN to disable transfer of config data */ 487 socfpga_fpga_clr_bitsl(priv, SOCFPGA_FPGMGR_CTL_OFST, 488 SOCFPGA_FPGMGR_CTL_AXICFGEN); 489 490 /* 491 * Step 12: 492 * - Write 4 to DCLKCNT 493 * - Wait for STATUS.DCNTDONE = 1 494 * - Clear W1C bit in STATUS.DCNTDONE 495 */ 496 if (socfpga_fpga_dclk_set_and_wait_clear(priv, 4)) 497 return -ETIMEDOUT; 498 499 /* Step 13: Wait for STATUS.MODE to report USER MODE */ 500 if (socfpga_fpga_wait_for_state(priv, SOCFPGA_FPGMGR_STAT_USER_MODE)) 501 return -ETIMEDOUT; 502 503 /* Step 14: Set CTRL.EN to 0 */ 504 socfpga_fpga_clr_bitsl(priv, SOCFPGA_FPGMGR_CTL_OFST, 505 SOCFPGA_FPGMGR_CTL_EN); 506 507 return 0; 508 } 509 510 /* Translate state register values to FPGA framework state */ 511 static const enum fpga_mgr_states socfpga_state_to_framework_state[] = { 512 [SOCFPGA_FPGMGR_STAT_POWER_OFF] = FPGA_MGR_STATE_POWER_OFF, 513 [SOCFPGA_FPGMGR_STAT_RESET] = FPGA_MGR_STATE_RESET, 514 [SOCFPGA_FPGMGR_STAT_CFG] = FPGA_MGR_STATE_WRITE_INIT, 515 [SOCFPGA_FPGMGR_STAT_INIT] = FPGA_MGR_STATE_WRITE_INIT, 516 [SOCFPGA_FPGMGR_STAT_USER_MODE] = FPGA_MGR_STATE_OPERATING, 517 [SOCFPGA_FPGMGR_STAT_UNKNOWN] = FPGA_MGR_STATE_UNKNOWN, 518 }; 519 520 static enum fpga_mgr_states socfpga_fpga_ops_state(struct fpga_manager *mgr) 521 { 522 struct socfpga_fpga_priv *priv = mgr->priv; 523 enum fpga_mgr_states ret; 524 u32 state; 525 526 state = socfpga_fpga_state_get(priv); 527 528 if (state < ARRAY_SIZE(socfpga_state_to_framework_state)) 529 ret = socfpga_state_to_framework_state[state]; 530 else 531 ret = FPGA_MGR_STATE_UNKNOWN; 532 533 return ret; 534 } 535 536 static const struct fpga_manager_ops socfpga_fpga_ops = { 537 .state = socfpga_fpga_ops_state, 538 .write_init = socfpga_fpga_ops_configure_init, 539 .write = socfpga_fpga_ops_configure_write, 540 .write_complete = socfpga_fpga_ops_configure_complete, 541 }; 542 543 static int socfpga_fpga_probe(struct platform_device *pdev) 544 { 545 struct device *dev = &pdev->dev; 546 struct socfpga_fpga_priv *priv; 547 struct fpga_manager *mgr; 548 int ret; 549 550 priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); 551 if (!priv) 552 return -ENOMEM; 553 554 priv->fpga_base_addr = devm_platform_ioremap_resource(pdev, 0); 555 if (IS_ERR(priv->fpga_base_addr)) 556 return PTR_ERR(priv->fpga_base_addr); 557 558 priv->fpga_data_addr = devm_platform_ioremap_resource(pdev, 1); 559 if (IS_ERR(priv->fpga_data_addr)) 560 return PTR_ERR(priv->fpga_data_addr); 561 562 priv->irq = platform_get_irq(pdev, 0); 563 if (priv->irq < 0) 564 return priv->irq; 565 566 ret = devm_request_irq(dev, priv->irq, socfpga_fpga_isr, 0, 567 dev_name(dev), priv); 568 if (ret) 569 return ret; 570 571 mgr = devm_fpga_mgr_register(dev, "Altera SOCFPGA FPGA Manager", 572 &socfpga_fpga_ops, priv); 573 return PTR_ERR_OR_ZERO(mgr); 574 } 575 576 #ifdef CONFIG_OF 577 static const struct of_device_id socfpga_fpga_of_match[] = { 578 { .compatible = "altr,socfpga-fpga-mgr", }, 579 {}, 580 }; 581 582 MODULE_DEVICE_TABLE(of, socfpga_fpga_of_match); 583 #endif 584 585 static struct platform_driver socfpga_fpga_driver = { 586 .probe = socfpga_fpga_probe, 587 .driver = { 588 .name = "socfpga_fpga_manager", 589 .of_match_table = of_match_ptr(socfpga_fpga_of_match), 590 }, 591 }; 592 593 module_platform_driver(socfpga_fpga_driver); 594 595 MODULE_AUTHOR("Alan Tull <atull@opensource.altera.com>"); 596 MODULE_DESCRIPTION("Altera SOCFPGA FPGA Manager"); 597 MODULE_LICENSE("GPL v2"); 598