ipl.c 52 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064
  1. /*
  2. * ipl/reipl/dump support for Linux on s390.
  3. *
  4. * Copyright IBM Corp. 2005, 2012
  5. * Author(s): Michael Holzheu <holzheu@de.ibm.com>
  6. * Heiko Carstens <heiko.carstens@de.ibm.com>
  7. * Volker Sameske <sameske@de.ibm.com>
  8. */
  9. #include <linux/types.h>
  10. #include <linux/module.h>
  11. #include <linux/device.h>
  12. #include <linux/delay.h>
  13. #include <linux/reboot.h>
  14. #include <linux/ctype.h>
  15. #include <linux/fs.h>
  16. #include <linux/gfp.h>
  17. #include <linux/crash_dump.h>
  18. #include <linux/debug_locks.h>
  19. #include <asm/ipl.h>
  20. #include <asm/smp.h>
  21. #include <asm/setup.h>
  22. #include <asm/cpcmd.h>
  23. #include <asm/cio.h>
  24. #include <asm/ebcdic.h>
  25. #include <asm/reset.h>
  26. #include <asm/sclp.h>
  27. #include <asm/checksum.h>
  28. #include <asm/debug.h>
  29. #include <asm/os_info.h>
  30. #include "entry.h"
  31. #define IPL_PARM_BLOCK_VERSION 0
  32. #define IPL_UNKNOWN_STR "unknown"
  33. #define IPL_CCW_STR "ccw"
  34. #define IPL_FCP_STR "fcp"
  35. #define IPL_FCP_DUMP_STR "fcp_dump"
  36. #define IPL_NSS_STR "nss"
  37. #define DUMP_CCW_STR "ccw"
  38. #define DUMP_FCP_STR "fcp"
  39. #define DUMP_NONE_STR "none"
  40. /*
  41. * Four shutdown trigger types are supported:
  42. * - panic
  43. * - halt
  44. * - power off
  45. * - reipl
  46. * - restart
  47. */
  48. #define ON_PANIC_STR "on_panic"
  49. #define ON_HALT_STR "on_halt"
  50. #define ON_POFF_STR "on_poff"
  51. #define ON_REIPL_STR "on_reboot"
  52. #define ON_RESTART_STR "on_restart"
  53. struct shutdown_action;
  54. struct shutdown_trigger {
  55. char *name;
  56. struct shutdown_action *action;
  57. };
  58. /*
  59. * The following shutdown action types are supported:
  60. */
  61. #define SHUTDOWN_ACTION_IPL_STR "ipl"
  62. #define SHUTDOWN_ACTION_REIPL_STR "reipl"
  63. #define SHUTDOWN_ACTION_DUMP_STR "dump"
  64. #define SHUTDOWN_ACTION_VMCMD_STR "vmcmd"
  65. #define SHUTDOWN_ACTION_STOP_STR "stop"
  66. #define SHUTDOWN_ACTION_DUMP_REIPL_STR "dump_reipl"
  67. struct shutdown_action {
  68. char *name;
  69. void (*fn) (struct shutdown_trigger *trigger);
  70. int (*init) (void);
  71. int init_rc;
  72. };
  73. static char *ipl_type_str(enum ipl_type type)
  74. {
  75. switch (type) {
  76. case IPL_TYPE_CCW:
  77. return IPL_CCW_STR;
  78. case IPL_TYPE_FCP:
  79. return IPL_FCP_STR;
  80. case IPL_TYPE_FCP_DUMP:
  81. return IPL_FCP_DUMP_STR;
  82. case IPL_TYPE_NSS:
  83. return IPL_NSS_STR;
  84. case IPL_TYPE_UNKNOWN:
  85. default:
  86. return IPL_UNKNOWN_STR;
  87. }
  88. }
  89. enum dump_type {
  90. DUMP_TYPE_NONE = 1,
  91. DUMP_TYPE_CCW = 2,
  92. DUMP_TYPE_FCP = 4,
  93. };
  94. static char *dump_type_str(enum dump_type type)
  95. {
  96. switch (type) {
  97. case DUMP_TYPE_NONE:
  98. return DUMP_NONE_STR;
  99. case DUMP_TYPE_CCW:
  100. return DUMP_CCW_STR;
  101. case DUMP_TYPE_FCP:
  102. return DUMP_FCP_STR;
  103. default:
  104. return NULL;
  105. }
  106. }
  107. /*
  108. * Must be in data section since the bss section
  109. * is not cleared when these are accessed.
  110. */
  111. static u16 ipl_devno __attribute__((__section__(".data"))) = 0;
  112. u32 ipl_flags __attribute__((__section__(".data"))) = 0;
  113. enum ipl_method {
  114. REIPL_METHOD_CCW_CIO,
  115. REIPL_METHOD_CCW_DIAG,
  116. REIPL_METHOD_CCW_VM,
  117. REIPL_METHOD_FCP_RO_DIAG,
  118. REIPL_METHOD_FCP_RW_DIAG,
  119. REIPL_METHOD_FCP_RO_VM,
  120. REIPL_METHOD_FCP_DUMP,
  121. REIPL_METHOD_NSS,
  122. REIPL_METHOD_NSS_DIAG,
  123. REIPL_METHOD_DEFAULT,
  124. };
  125. enum dump_method {
  126. DUMP_METHOD_NONE,
  127. DUMP_METHOD_CCW_CIO,
  128. DUMP_METHOD_CCW_DIAG,
  129. DUMP_METHOD_CCW_VM,
  130. DUMP_METHOD_FCP_DIAG,
  131. };
  132. static int diag308_set_works = 0;
  133. static struct ipl_parameter_block ipl_block;
  134. static int reipl_capabilities = IPL_TYPE_UNKNOWN;
  135. static enum ipl_type reipl_type = IPL_TYPE_UNKNOWN;
  136. static enum ipl_method reipl_method = REIPL_METHOD_DEFAULT;
  137. static struct ipl_parameter_block *reipl_block_fcp;
  138. static struct ipl_parameter_block *reipl_block_ccw;
  139. static struct ipl_parameter_block *reipl_block_nss;
  140. static struct ipl_parameter_block *reipl_block_actual;
  141. static int dump_capabilities = DUMP_TYPE_NONE;
  142. static enum dump_type dump_type = DUMP_TYPE_NONE;
  143. static enum dump_method dump_method = DUMP_METHOD_NONE;
  144. static struct ipl_parameter_block *dump_block_fcp;
  145. static struct ipl_parameter_block *dump_block_ccw;
  146. static struct sclp_ipl_info sclp_ipl_info;
  147. int diag308(unsigned long subcode, void *addr)
  148. {
  149. register unsigned long _addr asm("0") = (unsigned long) addr;
  150. register unsigned long _rc asm("1") = 0;
  151. asm volatile(
  152. " diag %0,%2,0x308\n"
  153. "0:\n"
  154. EX_TABLE(0b,0b)
  155. : "+d" (_addr), "+d" (_rc)
  156. : "d" (subcode) : "cc", "memory");
  157. return _rc;
  158. }
  159. EXPORT_SYMBOL_GPL(diag308);
  160. /* SYSFS */
  161. #define IPL_ATTR_SHOW_FN(_prefix, _name, _format, args...) \
  162. static ssize_t sys_##_prefix##_##_name##_show(struct kobject *kobj, \
  163. struct kobj_attribute *attr, \
  164. char *page) \
  165. { \
  166. return snprintf(page, PAGE_SIZE, _format, ##args); \
  167. }
  168. #define DEFINE_IPL_ATTR_RO(_prefix, _name, _format, _value) \
  169. IPL_ATTR_SHOW_FN(_prefix, _name, _format, _value) \
  170. static struct kobj_attribute sys_##_prefix##_##_name##_attr = \
  171. __ATTR(_name, S_IRUGO, sys_##_prefix##_##_name##_show, NULL)
  172. #define DEFINE_IPL_ATTR_RW(_prefix, _name, _fmt_out, _fmt_in, _value) \
  173. IPL_ATTR_SHOW_FN(_prefix, _name, _fmt_out, (unsigned long long) _value) \
  174. static ssize_t sys_##_prefix##_##_name##_store(struct kobject *kobj, \
  175. struct kobj_attribute *attr, \
  176. const char *buf, size_t len) \
  177. { \
  178. unsigned long long value; \
  179. if (sscanf(buf, _fmt_in, &value) != 1) \
  180. return -EINVAL; \
  181. _value = value; \
  182. return len; \
  183. } \
  184. static struct kobj_attribute sys_##_prefix##_##_name##_attr = \
  185. __ATTR(_name,(S_IRUGO | S_IWUSR), \
  186. sys_##_prefix##_##_name##_show, \
  187. sys_##_prefix##_##_name##_store)
  188. #define DEFINE_IPL_ATTR_STR_RW(_prefix, _name, _fmt_out, _fmt_in, _value)\
  189. IPL_ATTR_SHOW_FN(_prefix, _name, _fmt_out, _value) \
  190. static ssize_t sys_##_prefix##_##_name##_store(struct kobject *kobj, \
  191. struct kobj_attribute *attr, \
  192. const char *buf, size_t len) \
  193. { \
  194. strncpy(_value, buf, sizeof(_value) - 1); \
  195. strim(_value); \
  196. return len; \
  197. } \
  198. static struct kobj_attribute sys_##_prefix##_##_name##_attr = \
  199. __ATTR(_name,(S_IRUGO | S_IWUSR), \
  200. sys_##_prefix##_##_name##_show, \
  201. sys_##_prefix##_##_name##_store)
  202. static void make_attrs_ro(struct attribute **attrs)
  203. {
  204. while (*attrs) {
  205. (*attrs)->mode = S_IRUGO;
  206. attrs++;
  207. }
  208. }
  209. /*
  210. * ipl section
  211. */
  212. static __init enum ipl_type get_ipl_type(void)
  213. {
  214. struct ipl_parameter_block *ipl = IPL_PARMBLOCK_START;
  215. if (ipl_flags & IPL_NSS_VALID)
  216. return IPL_TYPE_NSS;
  217. if (!(ipl_flags & IPL_DEVNO_VALID))
  218. return IPL_TYPE_UNKNOWN;
  219. if (!(ipl_flags & IPL_PARMBLOCK_VALID))
  220. return IPL_TYPE_CCW;
  221. if (ipl->hdr.version > IPL_MAX_SUPPORTED_VERSION)
  222. return IPL_TYPE_UNKNOWN;
  223. if (ipl->hdr.pbt != DIAG308_IPL_TYPE_FCP)
  224. return IPL_TYPE_UNKNOWN;
  225. if (ipl->ipl_info.fcp.opt == DIAG308_IPL_OPT_DUMP)
  226. return IPL_TYPE_FCP_DUMP;
  227. return IPL_TYPE_FCP;
  228. }
  229. struct ipl_info ipl_info;
  230. EXPORT_SYMBOL_GPL(ipl_info);
  231. static ssize_t ipl_type_show(struct kobject *kobj, struct kobj_attribute *attr,
  232. char *page)
  233. {
  234. return sprintf(page, "%s\n", ipl_type_str(ipl_info.type));
  235. }
  236. static struct kobj_attribute sys_ipl_type_attr = __ATTR_RO(ipl_type);
  237. /* VM IPL PARM routines */
  238. static size_t reipl_get_ascii_vmparm(char *dest, size_t size,
  239. const struct ipl_parameter_block *ipb)
  240. {
  241. int i;
  242. size_t len;
  243. char has_lowercase = 0;
  244. len = 0;
  245. if ((ipb->ipl_info.ccw.vm_flags & DIAG308_VM_FLAGS_VP_VALID) &&
  246. (ipb->ipl_info.ccw.vm_parm_len > 0)) {
  247. len = min_t(size_t, size - 1, ipb->ipl_info.ccw.vm_parm_len);
  248. memcpy(dest, ipb->ipl_info.ccw.vm_parm, len);
  249. /* If at least one character is lowercase, we assume mixed
  250. * case; otherwise we convert everything to lowercase.
  251. */
  252. for (i = 0; i < len; i++)
  253. if ((dest[i] > 0x80 && dest[i] < 0x8a) || /* a-i */
  254. (dest[i] > 0x90 && dest[i] < 0x9a) || /* j-r */
  255. (dest[i] > 0xa1 && dest[i] < 0xaa)) { /* s-z */
  256. has_lowercase = 1;
  257. break;
  258. }
  259. if (!has_lowercase)
  260. EBC_TOLOWER(dest, len);
  261. EBCASC(dest, len);
  262. }
  263. dest[len] = 0;
  264. return len;
  265. }
  266. size_t append_ipl_vmparm(char *dest, size_t size)
  267. {
  268. size_t rc;
  269. rc = 0;
  270. if (diag308_set_works && (ipl_block.hdr.pbt == DIAG308_IPL_TYPE_CCW))
  271. rc = reipl_get_ascii_vmparm(dest, size, &ipl_block);
  272. else
  273. dest[0] = 0;
  274. return rc;
  275. }
  276. static ssize_t ipl_vm_parm_show(struct kobject *kobj,
  277. struct kobj_attribute *attr, char *page)
  278. {
  279. char parm[DIAG308_VMPARM_SIZE + 1] = {};
  280. append_ipl_vmparm(parm, sizeof(parm));
  281. return sprintf(page, "%s\n", parm);
  282. }
  283. static size_t scpdata_length(const char* buf, size_t count)
  284. {
  285. while (count) {
  286. if (buf[count - 1] != '\0' && buf[count - 1] != ' ')
  287. break;
  288. count--;
  289. }
  290. return count;
  291. }
  292. static size_t reipl_append_ascii_scpdata(char *dest, size_t size,
  293. const struct ipl_parameter_block *ipb)
  294. {
  295. size_t count;
  296. size_t i;
  297. int has_lowercase;
  298. count = min(size - 1, scpdata_length(ipb->ipl_info.fcp.scp_data,
  299. ipb->ipl_info.fcp.scp_data_len));
  300. if (!count)
  301. goto out;
  302. has_lowercase = 0;
  303. for (i = 0; i < count; i++) {
  304. if (!isascii(ipb->ipl_info.fcp.scp_data[i])) {
  305. count = 0;
  306. goto out;
  307. }
  308. if (!has_lowercase && islower(ipb->ipl_info.fcp.scp_data[i]))
  309. has_lowercase = 1;
  310. }
  311. if (has_lowercase)
  312. memcpy(dest, ipb->ipl_info.fcp.scp_data, count);
  313. else
  314. for (i = 0; i < count; i++)
  315. dest[i] = tolower(ipb->ipl_info.fcp.scp_data[i]);
  316. out:
  317. dest[count] = '\0';
  318. return count;
  319. }
  320. size_t append_ipl_scpdata(char *dest, size_t len)
  321. {
  322. size_t rc;
  323. rc = 0;
  324. if (ipl_block.hdr.pbt == DIAG308_IPL_TYPE_FCP)
  325. rc = reipl_append_ascii_scpdata(dest, len, &ipl_block);
  326. else
  327. dest[0] = 0;
  328. return rc;
  329. }
  330. static struct kobj_attribute sys_ipl_vm_parm_attr =
  331. __ATTR(parm, S_IRUGO, ipl_vm_parm_show, NULL);
  332. static ssize_t sys_ipl_device_show(struct kobject *kobj,
  333. struct kobj_attribute *attr, char *page)
  334. {
  335. struct ipl_parameter_block *ipl = IPL_PARMBLOCK_START;
  336. switch (ipl_info.type) {
  337. case IPL_TYPE_CCW:
  338. return sprintf(page, "0.0.%04x\n", ipl_devno);
  339. case IPL_TYPE_FCP:
  340. case IPL_TYPE_FCP_DUMP:
  341. return sprintf(page, "0.0.%04x\n", ipl->ipl_info.fcp.devno);
  342. default:
  343. return 0;
  344. }
  345. }
  346. static struct kobj_attribute sys_ipl_device_attr =
  347. __ATTR(device, S_IRUGO, sys_ipl_device_show, NULL);
  348. static ssize_t ipl_parameter_read(struct file *filp, struct kobject *kobj,
  349. struct bin_attribute *attr, char *buf,
  350. loff_t off, size_t count)
  351. {
  352. return memory_read_from_buffer(buf, count, &off, IPL_PARMBLOCK_START,
  353. IPL_PARMBLOCK_SIZE);
  354. }
  355. static struct bin_attribute ipl_parameter_attr =
  356. __BIN_ATTR(binary_parameter, S_IRUGO, ipl_parameter_read, NULL,
  357. PAGE_SIZE);
  358. static ssize_t ipl_scp_data_read(struct file *filp, struct kobject *kobj,
  359. struct bin_attribute *attr, char *buf,
  360. loff_t off, size_t count)
  361. {
  362. unsigned int size = IPL_PARMBLOCK_START->ipl_info.fcp.scp_data_len;
  363. void *scp_data = &IPL_PARMBLOCK_START->ipl_info.fcp.scp_data;
  364. return memory_read_from_buffer(buf, count, &off, scp_data, size);
  365. }
  366. static struct bin_attribute ipl_scp_data_attr =
  367. __BIN_ATTR(scp_data, S_IRUGO, ipl_scp_data_read, NULL, PAGE_SIZE);
  368. static struct bin_attribute *ipl_fcp_bin_attrs[] = {
  369. &ipl_parameter_attr,
  370. &ipl_scp_data_attr,
  371. NULL,
  372. };
  373. /* FCP ipl device attributes */
  374. DEFINE_IPL_ATTR_RO(ipl_fcp, wwpn, "0x%016llx\n", (unsigned long long)
  375. IPL_PARMBLOCK_START->ipl_info.fcp.wwpn);
  376. DEFINE_IPL_ATTR_RO(ipl_fcp, lun, "0x%016llx\n", (unsigned long long)
  377. IPL_PARMBLOCK_START->ipl_info.fcp.lun);
  378. DEFINE_IPL_ATTR_RO(ipl_fcp, bootprog, "%lld\n", (unsigned long long)
  379. IPL_PARMBLOCK_START->ipl_info.fcp.bootprog);
  380. DEFINE_IPL_ATTR_RO(ipl_fcp, br_lba, "%lld\n", (unsigned long long)
  381. IPL_PARMBLOCK_START->ipl_info.fcp.br_lba);
  382. static ssize_t ipl_ccw_loadparm_show(struct kobject *kobj,
  383. struct kobj_attribute *attr, char *page)
  384. {
  385. char loadparm[LOADPARM_LEN + 1] = {};
  386. if (!sclp_ipl_info.is_valid)
  387. return sprintf(page, "#unknown#\n");
  388. memcpy(loadparm, &sclp_ipl_info.loadparm, LOADPARM_LEN);
  389. EBCASC(loadparm, LOADPARM_LEN);
  390. strim(loadparm);
  391. return sprintf(page, "%s\n", loadparm);
  392. }
  393. static struct kobj_attribute sys_ipl_ccw_loadparm_attr =
  394. __ATTR(loadparm, 0444, ipl_ccw_loadparm_show, NULL);
  395. static struct attribute *ipl_fcp_attrs[] = {
  396. &sys_ipl_type_attr.attr,
  397. &sys_ipl_device_attr.attr,
  398. &sys_ipl_fcp_wwpn_attr.attr,
  399. &sys_ipl_fcp_lun_attr.attr,
  400. &sys_ipl_fcp_bootprog_attr.attr,
  401. &sys_ipl_fcp_br_lba_attr.attr,
  402. &sys_ipl_ccw_loadparm_attr.attr,
  403. NULL,
  404. };
  405. static struct attribute_group ipl_fcp_attr_group = {
  406. .attrs = ipl_fcp_attrs,
  407. .bin_attrs = ipl_fcp_bin_attrs,
  408. };
  409. /* CCW ipl device attributes */
  410. static struct attribute *ipl_ccw_attrs_vm[] = {
  411. &sys_ipl_type_attr.attr,
  412. &sys_ipl_device_attr.attr,
  413. &sys_ipl_ccw_loadparm_attr.attr,
  414. &sys_ipl_vm_parm_attr.attr,
  415. NULL,
  416. };
  417. static struct attribute *ipl_ccw_attrs_lpar[] = {
  418. &sys_ipl_type_attr.attr,
  419. &sys_ipl_device_attr.attr,
  420. &sys_ipl_ccw_loadparm_attr.attr,
  421. NULL,
  422. };
  423. static struct attribute_group ipl_ccw_attr_group_vm = {
  424. .attrs = ipl_ccw_attrs_vm,
  425. };
  426. static struct attribute_group ipl_ccw_attr_group_lpar = {
  427. .attrs = ipl_ccw_attrs_lpar
  428. };
  429. /* NSS ipl device attributes */
  430. DEFINE_IPL_ATTR_RO(ipl_nss, name, "%s\n", kernel_nss_name);
  431. static struct attribute *ipl_nss_attrs[] = {
  432. &sys_ipl_type_attr.attr,
  433. &sys_ipl_nss_name_attr.attr,
  434. &sys_ipl_ccw_loadparm_attr.attr,
  435. &sys_ipl_vm_parm_attr.attr,
  436. NULL,
  437. };
  438. static struct attribute_group ipl_nss_attr_group = {
  439. .attrs = ipl_nss_attrs,
  440. };
  441. /* UNKNOWN ipl device attributes */
  442. static struct attribute *ipl_unknown_attrs[] = {
  443. &sys_ipl_type_attr.attr,
  444. NULL,
  445. };
  446. static struct attribute_group ipl_unknown_attr_group = {
  447. .attrs = ipl_unknown_attrs,
  448. };
  449. static struct kset *ipl_kset;
  450. static void __ipl_run(void *unused)
  451. {
  452. diag308(DIAG308_IPL, NULL);
  453. if (MACHINE_IS_VM)
  454. __cpcmd("IPL", NULL, 0, NULL);
  455. else if (ipl_info.type == IPL_TYPE_CCW)
  456. reipl_ccw_dev(&ipl_info.data.ccw.dev_id);
  457. }
  458. static void ipl_run(struct shutdown_trigger *trigger)
  459. {
  460. smp_call_ipl_cpu(__ipl_run, NULL);
  461. }
  462. static int __init ipl_init(void)
  463. {
  464. int rc;
  465. ipl_kset = kset_create_and_add("ipl", NULL, firmware_kobj);
  466. if (!ipl_kset) {
  467. rc = -ENOMEM;
  468. goto out;
  469. }
  470. switch (ipl_info.type) {
  471. case IPL_TYPE_CCW:
  472. if (MACHINE_IS_VM)
  473. rc = sysfs_create_group(&ipl_kset->kobj,
  474. &ipl_ccw_attr_group_vm);
  475. else
  476. rc = sysfs_create_group(&ipl_kset->kobj,
  477. &ipl_ccw_attr_group_lpar);
  478. break;
  479. case IPL_TYPE_FCP:
  480. case IPL_TYPE_FCP_DUMP:
  481. rc = sysfs_create_group(&ipl_kset->kobj, &ipl_fcp_attr_group);
  482. break;
  483. case IPL_TYPE_NSS:
  484. rc = sysfs_create_group(&ipl_kset->kobj, &ipl_nss_attr_group);
  485. break;
  486. default:
  487. rc = sysfs_create_group(&ipl_kset->kobj,
  488. &ipl_unknown_attr_group);
  489. break;
  490. }
  491. out:
  492. if (rc)
  493. panic("ipl_init failed: rc = %i\n", rc);
  494. return 0;
  495. }
  496. static struct shutdown_action __refdata ipl_action = {
  497. .name = SHUTDOWN_ACTION_IPL_STR,
  498. .fn = ipl_run,
  499. .init = ipl_init,
  500. };
  501. /*
  502. * reipl shutdown action: Reboot Linux on shutdown.
  503. */
  504. /* VM IPL PARM attributes */
  505. static ssize_t reipl_generic_vmparm_show(struct ipl_parameter_block *ipb,
  506. char *page)
  507. {
  508. char vmparm[DIAG308_VMPARM_SIZE + 1] = {};
  509. reipl_get_ascii_vmparm(vmparm, sizeof(vmparm), ipb);
  510. return sprintf(page, "%s\n", vmparm);
  511. }
  512. static ssize_t reipl_generic_vmparm_store(struct ipl_parameter_block *ipb,
  513. size_t vmparm_max,
  514. const char *buf, size_t len)
  515. {
  516. int i, ip_len;
  517. /* ignore trailing newline */
  518. ip_len = len;
  519. if ((len > 0) && (buf[len - 1] == '\n'))
  520. ip_len--;
  521. if (ip_len > vmparm_max)
  522. return -EINVAL;
  523. /* parm is used to store kernel options, check for common chars */
  524. for (i = 0; i < ip_len; i++)
  525. if (!(isalnum(buf[i]) || isascii(buf[i]) || isprint(buf[i])))
  526. return -EINVAL;
  527. memset(ipb->ipl_info.ccw.vm_parm, 0, DIAG308_VMPARM_SIZE);
  528. ipb->ipl_info.ccw.vm_parm_len = ip_len;
  529. if (ip_len > 0) {
  530. ipb->ipl_info.ccw.vm_flags |= DIAG308_VM_FLAGS_VP_VALID;
  531. memcpy(ipb->ipl_info.ccw.vm_parm, buf, ip_len);
  532. ASCEBC(ipb->ipl_info.ccw.vm_parm, ip_len);
  533. } else {
  534. ipb->ipl_info.ccw.vm_flags &= ~DIAG308_VM_FLAGS_VP_VALID;
  535. }
  536. return len;
  537. }
  538. /* NSS wrapper */
  539. static ssize_t reipl_nss_vmparm_show(struct kobject *kobj,
  540. struct kobj_attribute *attr, char *page)
  541. {
  542. return reipl_generic_vmparm_show(reipl_block_nss, page);
  543. }
  544. static ssize_t reipl_nss_vmparm_store(struct kobject *kobj,
  545. struct kobj_attribute *attr,
  546. const char *buf, size_t len)
  547. {
  548. return reipl_generic_vmparm_store(reipl_block_nss, 56, buf, len);
  549. }
  550. /* CCW wrapper */
  551. static ssize_t reipl_ccw_vmparm_show(struct kobject *kobj,
  552. struct kobj_attribute *attr, char *page)
  553. {
  554. return reipl_generic_vmparm_show(reipl_block_ccw, page);
  555. }
  556. static ssize_t reipl_ccw_vmparm_store(struct kobject *kobj,
  557. struct kobj_attribute *attr,
  558. const char *buf, size_t len)
  559. {
  560. return reipl_generic_vmparm_store(reipl_block_ccw, 64, buf, len);
  561. }
  562. static struct kobj_attribute sys_reipl_nss_vmparm_attr =
  563. __ATTR(parm, S_IRUGO | S_IWUSR, reipl_nss_vmparm_show,
  564. reipl_nss_vmparm_store);
  565. static struct kobj_attribute sys_reipl_ccw_vmparm_attr =
  566. __ATTR(parm, S_IRUGO | S_IWUSR, reipl_ccw_vmparm_show,
  567. reipl_ccw_vmparm_store);
  568. /* FCP reipl device attributes */
  569. static ssize_t reipl_fcp_scpdata_read(struct file *filp, struct kobject *kobj,
  570. struct bin_attribute *attr,
  571. char *buf, loff_t off, size_t count)
  572. {
  573. size_t size = reipl_block_fcp->ipl_info.fcp.scp_data_len;
  574. void *scp_data = reipl_block_fcp->ipl_info.fcp.scp_data;
  575. return memory_read_from_buffer(buf, count, &off, scp_data, size);
  576. }
  577. static ssize_t reipl_fcp_scpdata_write(struct file *filp, struct kobject *kobj,
  578. struct bin_attribute *attr,
  579. char *buf, loff_t off, size_t count)
  580. {
  581. size_t padding;
  582. size_t scpdata_len;
  583. if (off < 0)
  584. return -EINVAL;
  585. if (off >= DIAG308_SCPDATA_SIZE)
  586. return -ENOSPC;
  587. if (count > DIAG308_SCPDATA_SIZE - off)
  588. count = DIAG308_SCPDATA_SIZE - off;
  589. memcpy(reipl_block_fcp->ipl_info.fcp.scp_data, buf + off, count);
  590. scpdata_len = off + count;
  591. if (scpdata_len % 8) {
  592. padding = 8 - (scpdata_len % 8);
  593. memset(reipl_block_fcp->ipl_info.fcp.scp_data + scpdata_len,
  594. 0, padding);
  595. scpdata_len += padding;
  596. }
  597. reipl_block_fcp->ipl_info.fcp.scp_data_len = scpdata_len;
  598. reipl_block_fcp->hdr.len = IPL_PARM_BLK_FCP_LEN + scpdata_len;
  599. reipl_block_fcp->hdr.blk0_len = IPL_PARM_BLK0_FCP_LEN + scpdata_len;
  600. return count;
  601. }
  602. static struct bin_attribute sys_reipl_fcp_scp_data_attr =
  603. __BIN_ATTR(scp_data, (S_IRUGO | S_IWUSR), reipl_fcp_scpdata_read,
  604. reipl_fcp_scpdata_write, PAGE_SIZE);
  605. static struct bin_attribute *reipl_fcp_bin_attrs[] = {
  606. &sys_reipl_fcp_scp_data_attr,
  607. NULL,
  608. };
  609. DEFINE_IPL_ATTR_RW(reipl_fcp, wwpn, "0x%016llx\n", "%llx\n",
  610. reipl_block_fcp->ipl_info.fcp.wwpn);
  611. DEFINE_IPL_ATTR_RW(reipl_fcp, lun, "0x%016llx\n", "%llx\n",
  612. reipl_block_fcp->ipl_info.fcp.lun);
  613. DEFINE_IPL_ATTR_RW(reipl_fcp, bootprog, "%lld\n", "%lld\n",
  614. reipl_block_fcp->ipl_info.fcp.bootprog);
  615. DEFINE_IPL_ATTR_RW(reipl_fcp, br_lba, "%lld\n", "%lld\n",
  616. reipl_block_fcp->ipl_info.fcp.br_lba);
  617. DEFINE_IPL_ATTR_RW(reipl_fcp, device, "0.0.%04llx\n", "0.0.%llx\n",
  618. reipl_block_fcp->ipl_info.fcp.devno);
  619. static void reipl_get_ascii_loadparm(char *loadparm,
  620. struct ipl_parameter_block *ibp)
  621. {
  622. memcpy(loadparm, ibp->hdr.loadparm, LOADPARM_LEN);
  623. EBCASC(loadparm, LOADPARM_LEN);
  624. loadparm[LOADPARM_LEN] = 0;
  625. strim(loadparm);
  626. }
  627. static ssize_t reipl_generic_loadparm_show(struct ipl_parameter_block *ipb,
  628. char *page)
  629. {
  630. char buf[LOADPARM_LEN + 1];
  631. reipl_get_ascii_loadparm(buf, ipb);
  632. return sprintf(page, "%s\n", buf);
  633. }
  634. static ssize_t reipl_generic_loadparm_store(struct ipl_parameter_block *ipb,
  635. const char *buf, size_t len)
  636. {
  637. int i, lp_len;
  638. /* ignore trailing newline */
  639. lp_len = len;
  640. if ((len > 0) && (buf[len - 1] == '\n'))
  641. lp_len--;
  642. /* loadparm can have max 8 characters and must not start with a blank */
  643. if ((lp_len > LOADPARM_LEN) || ((lp_len > 0) && (buf[0] == ' ')))
  644. return -EINVAL;
  645. /* loadparm can only contain "a-z,A-Z,0-9,SP,." */
  646. for (i = 0; i < lp_len; i++) {
  647. if (isalpha(buf[i]) || isdigit(buf[i]) || (buf[i] == ' ') ||
  648. (buf[i] == '.'))
  649. continue;
  650. return -EINVAL;
  651. }
  652. /* initialize loadparm with blanks */
  653. memset(ipb->hdr.loadparm, ' ', LOADPARM_LEN);
  654. /* copy and convert to ebcdic */
  655. memcpy(ipb->hdr.loadparm, buf, lp_len);
  656. ASCEBC(ipb->hdr.loadparm, LOADPARM_LEN);
  657. return len;
  658. }
  659. /* FCP wrapper */
  660. static ssize_t reipl_fcp_loadparm_show(struct kobject *kobj,
  661. struct kobj_attribute *attr, char *page)
  662. {
  663. return reipl_generic_loadparm_show(reipl_block_fcp, page);
  664. }
  665. static ssize_t reipl_fcp_loadparm_store(struct kobject *kobj,
  666. struct kobj_attribute *attr,
  667. const char *buf, size_t len)
  668. {
  669. return reipl_generic_loadparm_store(reipl_block_fcp, buf, len);
  670. }
  671. static struct kobj_attribute sys_reipl_fcp_loadparm_attr =
  672. __ATTR(loadparm, S_IRUGO | S_IWUSR, reipl_fcp_loadparm_show,
  673. reipl_fcp_loadparm_store);
  674. static struct attribute *reipl_fcp_attrs[] = {
  675. &sys_reipl_fcp_device_attr.attr,
  676. &sys_reipl_fcp_wwpn_attr.attr,
  677. &sys_reipl_fcp_lun_attr.attr,
  678. &sys_reipl_fcp_bootprog_attr.attr,
  679. &sys_reipl_fcp_br_lba_attr.attr,
  680. &sys_reipl_fcp_loadparm_attr.attr,
  681. NULL,
  682. };
  683. static struct attribute_group reipl_fcp_attr_group = {
  684. .attrs = reipl_fcp_attrs,
  685. .bin_attrs = reipl_fcp_bin_attrs,
  686. };
  687. /* CCW reipl device attributes */
  688. DEFINE_IPL_ATTR_RW(reipl_ccw, device, "0.0.%04llx\n", "0.0.%llx\n",
  689. reipl_block_ccw->ipl_info.ccw.devno);
  690. /* NSS wrapper */
  691. static ssize_t reipl_nss_loadparm_show(struct kobject *kobj,
  692. struct kobj_attribute *attr, char *page)
  693. {
  694. return reipl_generic_loadparm_show(reipl_block_nss, page);
  695. }
  696. static ssize_t reipl_nss_loadparm_store(struct kobject *kobj,
  697. struct kobj_attribute *attr,
  698. const char *buf, size_t len)
  699. {
  700. return reipl_generic_loadparm_store(reipl_block_nss, buf, len);
  701. }
  702. /* CCW wrapper */
  703. static ssize_t reipl_ccw_loadparm_show(struct kobject *kobj,
  704. struct kobj_attribute *attr, char *page)
  705. {
  706. return reipl_generic_loadparm_show(reipl_block_ccw, page);
  707. }
  708. static ssize_t reipl_ccw_loadparm_store(struct kobject *kobj,
  709. struct kobj_attribute *attr,
  710. const char *buf, size_t len)
  711. {
  712. return reipl_generic_loadparm_store(reipl_block_ccw, buf, len);
  713. }
  714. static struct kobj_attribute sys_reipl_ccw_loadparm_attr =
  715. __ATTR(loadparm, S_IRUGO | S_IWUSR, reipl_ccw_loadparm_show,
  716. reipl_ccw_loadparm_store);
  717. static struct attribute *reipl_ccw_attrs_vm[] = {
  718. &sys_reipl_ccw_device_attr.attr,
  719. &sys_reipl_ccw_loadparm_attr.attr,
  720. &sys_reipl_ccw_vmparm_attr.attr,
  721. NULL,
  722. };
  723. static struct attribute *reipl_ccw_attrs_lpar[] = {
  724. &sys_reipl_ccw_device_attr.attr,
  725. &sys_reipl_ccw_loadparm_attr.attr,
  726. NULL,
  727. };
  728. static struct attribute_group reipl_ccw_attr_group_vm = {
  729. .name = IPL_CCW_STR,
  730. .attrs = reipl_ccw_attrs_vm,
  731. };
  732. static struct attribute_group reipl_ccw_attr_group_lpar = {
  733. .name = IPL_CCW_STR,
  734. .attrs = reipl_ccw_attrs_lpar,
  735. };
  736. /* NSS reipl device attributes */
  737. static void reipl_get_ascii_nss_name(char *dst,
  738. struct ipl_parameter_block *ipb)
  739. {
  740. memcpy(dst, ipb->ipl_info.ccw.nss_name, NSS_NAME_SIZE);
  741. EBCASC(dst, NSS_NAME_SIZE);
  742. dst[NSS_NAME_SIZE] = 0;
  743. }
  744. static ssize_t reipl_nss_name_show(struct kobject *kobj,
  745. struct kobj_attribute *attr, char *page)
  746. {
  747. char nss_name[NSS_NAME_SIZE + 1] = {};
  748. reipl_get_ascii_nss_name(nss_name, reipl_block_nss);
  749. return sprintf(page, "%s\n", nss_name);
  750. }
  751. static ssize_t reipl_nss_name_store(struct kobject *kobj,
  752. struct kobj_attribute *attr,
  753. const char *buf, size_t len)
  754. {
  755. int nss_len;
  756. /* ignore trailing newline */
  757. nss_len = len;
  758. if ((len > 0) && (buf[len - 1] == '\n'))
  759. nss_len--;
  760. if (nss_len > NSS_NAME_SIZE)
  761. return -EINVAL;
  762. memset(reipl_block_nss->ipl_info.ccw.nss_name, 0x40, NSS_NAME_SIZE);
  763. if (nss_len > 0) {
  764. reipl_block_nss->ipl_info.ccw.vm_flags |=
  765. DIAG308_VM_FLAGS_NSS_VALID;
  766. memcpy(reipl_block_nss->ipl_info.ccw.nss_name, buf, nss_len);
  767. ASCEBC(reipl_block_nss->ipl_info.ccw.nss_name, nss_len);
  768. EBC_TOUPPER(reipl_block_nss->ipl_info.ccw.nss_name, nss_len);
  769. } else {
  770. reipl_block_nss->ipl_info.ccw.vm_flags &=
  771. ~DIAG308_VM_FLAGS_NSS_VALID;
  772. }
  773. return len;
  774. }
  775. static struct kobj_attribute sys_reipl_nss_name_attr =
  776. __ATTR(name, S_IRUGO | S_IWUSR, reipl_nss_name_show,
  777. reipl_nss_name_store);
  778. static struct kobj_attribute sys_reipl_nss_loadparm_attr =
  779. __ATTR(loadparm, S_IRUGO | S_IWUSR, reipl_nss_loadparm_show,
  780. reipl_nss_loadparm_store);
  781. static struct attribute *reipl_nss_attrs[] = {
  782. &sys_reipl_nss_name_attr.attr,
  783. &sys_reipl_nss_loadparm_attr.attr,
  784. &sys_reipl_nss_vmparm_attr.attr,
  785. NULL,
  786. };
  787. static struct attribute_group reipl_nss_attr_group = {
  788. .name = IPL_NSS_STR,
  789. .attrs = reipl_nss_attrs,
  790. };
  791. static void set_reipl_block_actual(struct ipl_parameter_block *reipl_block)
  792. {
  793. reipl_block_actual = reipl_block;
  794. os_info_entry_add(OS_INFO_REIPL_BLOCK, reipl_block_actual,
  795. reipl_block->hdr.len);
  796. }
  797. /* reipl type */
  798. static int reipl_set_type(enum ipl_type type)
  799. {
  800. if (!(reipl_capabilities & type))
  801. return -EINVAL;
  802. switch(type) {
  803. case IPL_TYPE_CCW:
  804. if (diag308_set_works)
  805. reipl_method = REIPL_METHOD_CCW_DIAG;
  806. else if (MACHINE_IS_VM)
  807. reipl_method = REIPL_METHOD_CCW_VM;
  808. else
  809. reipl_method = REIPL_METHOD_CCW_CIO;
  810. set_reipl_block_actual(reipl_block_ccw);
  811. break;
  812. case IPL_TYPE_FCP:
  813. if (diag308_set_works)
  814. reipl_method = REIPL_METHOD_FCP_RW_DIAG;
  815. else if (MACHINE_IS_VM)
  816. reipl_method = REIPL_METHOD_FCP_RO_VM;
  817. else
  818. reipl_method = REIPL_METHOD_FCP_RO_DIAG;
  819. set_reipl_block_actual(reipl_block_fcp);
  820. break;
  821. case IPL_TYPE_FCP_DUMP:
  822. reipl_method = REIPL_METHOD_FCP_DUMP;
  823. break;
  824. case IPL_TYPE_NSS:
  825. if (diag308_set_works)
  826. reipl_method = REIPL_METHOD_NSS_DIAG;
  827. else
  828. reipl_method = REIPL_METHOD_NSS;
  829. set_reipl_block_actual(reipl_block_nss);
  830. break;
  831. case IPL_TYPE_UNKNOWN:
  832. reipl_method = REIPL_METHOD_DEFAULT;
  833. break;
  834. default:
  835. BUG();
  836. }
  837. reipl_type = type;
  838. return 0;
  839. }
  840. static ssize_t reipl_type_show(struct kobject *kobj,
  841. struct kobj_attribute *attr, char *page)
  842. {
  843. return sprintf(page, "%s\n", ipl_type_str(reipl_type));
  844. }
  845. static ssize_t reipl_type_store(struct kobject *kobj,
  846. struct kobj_attribute *attr,
  847. const char *buf, size_t len)
  848. {
  849. int rc = -EINVAL;
  850. if (strncmp(buf, IPL_CCW_STR, strlen(IPL_CCW_STR)) == 0)
  851. rc = reipl_set_type(IPL_TYPE_CCW);
  852. else if (strncmp(buf, IPL_FCP_STR, strlen(IPL_FCP_STR)) == 0)
  853. rc = reipl_set_type(IPL_TYPE_FCP);
  854. else if (strncmp(buf, IPL_NSS_STR, strlen(IPL_NSS_STR)) == 0)
  855. rc = reipl_set_type(IPL_TYPE_NSS);
  856. return (rc != 0) ? rc : len;
  857. }
  858. static struct kobj_attribute reipl_type_attr =
  859. __ATTR(reipl_type, 0644, reipl_type_show, reipl_type_store);
  860. static struct kset *reipl_kset;
  861. static struct kset *reipl_fcp_kset;
  862. static void get_ipl_string(char *dst, struct ipl_parameter_block *ipb,
  863. const enum ipl_method m)
  864. {
  865. char loadparm[LOADPARM_LEN + 1] = {};
  866. char vmparm[DIAG308_VMPARM_SIZE + 1] = {};
  867. char nss_name[NSS_NAME_SIZE + 1] = {};
  868. size_t pos = 0;
  869. reipl_get_ascii_loadparm(loadparm, ipb);
  870. reipl_get_ascii_nss_name(nss_name, ipb);
  871. reipl_get_ascii_vmparm(vmparm, sizeof(vmparm), ipb);
  872. switch (m) {
  873. case REIPL_METHOD_CCW_VM:
  874. pos = sprintf(dst, "IPL %X CLEAR", ipb->ipl_info.ccw.devno);
  875. break;
  876. case REIPL_METHOD_NSS:
  877. pos = sprintf(dst, "IPL %s", nss_name);
  878. break;
  879. default:
  880. break;
  881. }
  882. if (strlen(loadparm) > 0)
  883. pos += sprintf(dst + pos, " LOADPARM '%s'", loadparm);
  884. if (strlen(vmparm) > 0)
  885. sprintf(dst + pos, " PARM %s", vmparm);
  886. }
  887. static void __reipl_run(void *unused)
  888. {
  889. struct ccw_dev_id devid;
  890. static char buf[128];
  891. switch (reipl_method) {
  892. case REIPL_METHOD_CCW_CIO:
  893. devid.devno = reipl_block_ccw->ipl_info.ccw.devno;
  894. devid.ssid = 0;
  895. reipl_ccw_dev(&devid);
  896. break;
  897. case REIPL_METHOD_CCW_VM:
  898. get_ipl_string(buf, reipl_block_ccw, REIPL_METHOD_CCW_VM);
  899. __cpcmd(buf, NULL, 0, NULL);
  900. break;
  901. case REIPL_METHOD_CCW_DIAG:
  902. diag308(DIAG308_SET, reipl_block_ccw);
  903. diag308(DIAG308_IPL, NULL);
  904. break;
  905. case REIPL_METHOD_FCP_RW_DIAG:
  906. diag308(DIAG308_SET, reipl_block_fcp);
  907. diag308(DIAG308_IPL, NULL);
  908. break;
  909. case REIPL_METHOD_FCP_RO_DIAG:
  910. diag308(DIAG308_IPL, NULL);
  911. break;
  912. case REIPL_METHOD_FCP_RO_VM:
  913. __cpcmd("IPL", NULL, 0, NULL);
  914. break;
  915. case REIPL_METHOD_NSS_DIAG:
  916. diag308(DIAG308_SET, reipl_block_nss);
  917. diag308(DIAG308_IPL, NULL);
  918. break;
  919. case REIPL_METHOD_NSS:
  920. get_ipl_string(buf, reipl_block_nss, REIPL_METHOD_NSS);
  921. __cpcmd(buf, NULL, 0, NULL);
  922. break;
  923. case REIPL_METHOD_DEFAULT:
  924. if (MACHINE_IS_VM)
  925. __cpcmd("IPL", NULL, 0, NULL);
  926. diag308(DIAG308_IPL, NULL);
  927. break;
  928. case REIPL_METHOD_FCP_DUMP:
  929. break;
  930. }
  931. disabled_wait((unsigned long) __builtin_return_address(0));
  932. }
  933. static void reipl_run(struct shutdown_trigger *trigger)
  934. {
  935. smp_call_ipl_cpu(__reipl_run, NULL);
  936. }
  937. static void reipl_block_ccw_init(struct ipl_parameter_block *ipb)
  938. {
  939. ipb->hdr.len = IPL_PARM_BLK_CCW_LEN;
  940. ipb->hdr.version = IPL_PARM_BLOCK_VERSION;
  941. ipb->hdr.blk0_len = IPL_PARM_BLK0_CCW_LEN;
  942. ipb->hdr.pbt = DIAG308_IPL_TYPE_CCW;
  943. }
  944. static void reipl_block_ccw_fill_parms(struct ipl_parameter_block *ipb)
  945. {
  946. /* LOADPARM */
  947. /* check if read scp info worked and set loadparm */
  948. if (sclp_ipl_info.is_valid)
  949. memcpy(ipb->hdr.loadparm, &sclp_ipl_info.loadparm, LOADPARM_LEN);
  950. else
  951. /* read scp info failed: set empty loadparm (EBCDIC blanks) */
  952. memset(ipb->hdr.loadparm, 0x40, LOADPARM_LEN);
  953. ipb->hdr.flags = DIAG308_FLAGS_LP_VALID;
  954. /* VM PARM */
  955. if (MACHINE_IS_VM && diag308_set_works &&
  956. (ipl_block.ipl_info.ccw.vm_flags & DIAG308_VM_FLAGS_VP_VALID)) {
  957. ipb->ipl_info.ccw.vm_flags |= DIAG308_VM_FLAGS_VP_VALID;
  958. ipb->ipl_info.ccw.vm_parm_len =
  959. ipl_block.ipl_info.ccw.vm_parm_len;
  960. memcpy(ipb->ipl_info.ccw.vm_parm,
  961. ipl_block.ipl_info.ccw.vm_parm, DIAG308_VMPARM_SIZE);
  962. }
  963. }
  964. static int __init reipl_nss_init(void)
  965. {
  966. int rc;
  967. if (!MACHINE_IS_VM)
  968. return 0;
  969. reipl_block_nss = (void *) get_zeroed_page(GFP_KERNEL);
  970. if (!reipl_block_nss)
  971. return -ENOMEM;
  972. if (!diag308_set_works)
  973. sys_reipl_nss_vmparm_attr.attr.mode = S_IRUGO;
  974. rc = sysfs_create_group(&reipl_kset->kobj, &reipl_nss_attr_group);
  975. if (rc)
  976. return rc;
  977. reipl_block_ccw_init(reipl_block_nss);
  978. if (ipl_info.type == IPL_TYPE_NSS) {
  979. memset(reipl_block_nss->ipl_info.ccw.nss_name,
  980. ' ', NSS_NAME_SIZE);
  981. memcpy(reipl_block_nss->ipl_info.ccw.nss_name,
  982. kernel_nss_name, strlen(kernel_nss_name));
  983. ASCEBC(reipl_block_nss->ipl_info.ccw.nss_name, NSS_NAME_SIZE);
  984. reipl_block_nss->ipl_info.ccw.vm_flags |=
  985. DIAG308_VM_FLAGS_NSS_VALID;
  986. reipl_block_ccw_fill_parms(reipl_block_nss);
  987. }
  988. reipl_capabilities |= IPL_TYPE_NSS;
  989. return 0;
  990. }
  991. static int __init reipl_ccw_init(void)
  992. {
  993. int rc;
  994. reipl_block_ccw = (void *) get_zeroed_page(GFP_KERNEL);
  995. if (!reipl_block_ccw)
  996. return -ENOMEM;
  997. if (MACHINE_IS_VM) {
  998. if (!diag308_set_works)
  999. sys_reipl_ccw_vmparm_attr.attr.mode = S_IRUGO;
  1000. rc = sysfs_create_group(&reipl_kset->kobj,
  1001. &reipl_ccw_attr_group_vm);
  1002. } else {
  1003. if(!diag308_set_works)
  1004. sys_reipl_ccw_loadparm_attr.attr.mode = S_IRUGO;
  1005. rc = sysfs_create_group(&reipl_kset->kobj,
  1006. &reipl_ccw_attr_group_lpar);
  1007. }
  1008. if (rc)
  1009. return rc;
  1010. reipl_block_ccw_init(reipl_block_ccw);
  1011. if (ipl_info.type == IPL_TYPE_CCW) {
  1012. reipl_block_ccw->ipl_info.ccw.devno = ipl_devno;
  1013. reipl_block_ccw_fill_parms(reipl_block_ccw);
  1014. }
  1015. reipl_capabilities |= IPL_TYPE_CCW;
  1016. return 0;
  1017. }
  1018. static int __init reipl_fcp_init(void)
  1019. {
  1020. int rc;
  1021. if (!diag308_set_works) {
  1022. if (ipl_info.type == IPL_TYPE_FCP) {
  1023. make_attrs_ro(reipl_fcp_attrs);
  1024. sys_reipl_fcp_scp_data_attr.attr.mode = S_IRUGO;
  1025. } else
  1026. return 0;
  1027. }
  1028. reipl_block_fcp = (void *) get_zeroed_page(GFP_KERNEL);
  1029. if (!reipl_block_fcp)
  1030. return -ENOMEM;
  1031. /* sysfs: create fcp kset for mixing attr group and bin attrs */
  1032. reipl_fcp_kset = kset_create_and_add(IPL_FCP_STR, NULL,
  1033. &reipl_kset->kobj);
  1034. if (!reipl_fcp_kset) {
  1035. free_page((unsigned long) reipl_block_fcp);
  1036. return -ENOMEM;
  1037. }
  1038. rc = sysfs_create_group(&reipl_fcp_kset->kobj, &reipl_fcp_attr_group);
  1039. if (rc) {
  1040. kset_unregister(reipl_fcp_kset);
  1041. free_page((unsigned long) reipl_block_fcp);
  1042. return rc;
  1043. }
  1044. if (ipl_info.type == IPL_TYPE_FCP) {
  1045. memcpy(reipl_block_fcp, IPL_PARMBLOCK_START, PAGE_SIZE);
  1046. /*
  1047. * Fix loadparm: There are systems where the (SCSI) LOADPARM
  1048. * is invalid in the SCSI IPL parameter block, so take it
  1049. * always from sclp_ipl_info.
  1050. */
  1051. memcpy(reipl_block_fcp->hdr.loadparm, sclp_ipl_info.loadparm,
  1052. LOADPARM_LEN);
  1053. } else {
  1054. reipl_block_fcp->hdr.len = IPL_PARM_BLK_FCP_LEN;
  1055. reipl_block_fcp->hdr.version = IPL_PARM_BLOCK_VERSION;
  1056. reipl_block_fcp->hdr.blk0_len = IPL_PARM_BLK0_FCP_LEN;
  1057. reipl_block_fcp->hdr.pbt = DIAG308_IPL_TYPE_FCP;
  1058. reipl_block_fcp->ipl_info.fcp.opt = DIAG308_IPL_OPT_IPL;
  1059. }
  1060. reipl_capabilities |= IPL_TYPE_FCP;
  1061. return 0;
  1062. }
  1063. static int __init reipl_type_init(void)
  1064. {
  1065. enum ipl_type reipl_type = ipl_info.type;
  1066. struct ipl_parameter_block *reipl_block;
  1067. unsigned long size;
  1068. reipl_block = os_info_old_entry(OS_INFO_REIPL_BLOCK, &size);
  1069. if (!reipl_block)
  1070. goto out;
  1071. /*
  1072. * If we have an OS info reipl block, this will be used
  1073. */
  1074. if (reipl_block->hdr.pbt == DIAG308_IPL_TYPE_FCP) {
  1075. memcpy(reipl_block_fcp, reipl_block, size);
  1076. reipl_type = IPL_TYPE_FCP;
  1077. } else if (reipl_block->hdr.pbt == DIAG308_IPL_TYPE_CCW) {
  1078. memcpy(reipl_block_ccw, reipl_block, size);
  1079. reipl_type = IPL_TYPE_CCW;
  1080. }
  1081. out:
  1082. return reipl_set_type(reipl_type);
  1083. }
  1084. static int __init reipl_init(void)
  1085. {
  1086. int rc;
  1087. reipl_kset = kset_create_and_add("reipl", NULL, firmware_kobj);
  1088. if (!reipl_kset)
  1089. return -ENOMEM;
  1090. rc = sysfs_create_file(&reipl_kset->kobj, &reipl_type_attr.attr);
  1091. if (rc) {
  1092. kset_unregister(reipl_kset);
  1093. return rc;
  1094. }
  1095. rc = reipl_ccw_init();
  1096. if (rc)
  1097. return rc;
  1098. rc = reipl_fcp_init();
  1099. if (rc)
  1100. return rc;
  1101. rc = reipl_nss_init();
  1102. if (rc)
  1103. return rc;
  1104. return reipl_type_init();
  1105. }
  1106. static struct shutdown_action __refdata reipl_action = {
  1107. .name = SHUTDOWN_ACTION_REIPL_STR,
  1108. .fn = reipl_run,
  1109. .init = reipl_init,
  1110. };
  1111. /*
  1112. * dump shutdown action: Dump Linux on shutdown.
  1113. */
  1114. /* FCP dump device attributes */
  1115. DEFINE_IPL_ATTR_RW(dump_fcp, wwpn, "0x%016llx\n", "%llx\n",
  1116. dump_block_fcp->ipl_info.fcp.wwpn);
  1117. DEFINE_IPL_ATTR_RW(dump_fcp, lun, "0x%016llx\n", "%llx\n",
  1118. dump_block_fcp->ipl_info.fcp.lun);
  1119. DEFINE_IPL_ATTR_RW(dump_fcp, bootprog, "%lld\n", "%lld\n",
  1120. dump_block_fcp->ipl_info.fcp.bootprog);
  1121. DEFINE_IPL_ATTR_RW(dump_fcp, br_lba, "%lld\n", "%lld\n",
  1122. dump_block_fcp->ipl_info.fcp.br_lba);
  1123. DEFINE_IPL_ATTR_RW(dump_fcp, device, "0.0.%04llx\n", "0.0.%llx\n",
  1124. dump_block_fcp->ipl_info.fcp.devno);
  1125. static struct attribute *dump_fcp_attrs[] = {
  1126. &sys_dump_fcp_device_attr.attr,
  1127. &sys_dump_fcp_wwpn_attr.attr,
  1128. &sys_dump_fcp_lun_attr.attr,
  1129. &sys_dump_fcp_bootprog_attr.attr,
  1130. &sys_dump_fcp_br_lba_attr.attr,
  1131. NULL,
  1132. };
  1133. static struct attribute_group dump_fcp_attr_group = {
  1134. .name = IPL_FCP_STR,
  1135. .attrs = dump_fcp_attrs,
  1136. };
  1137. /* CCW dump device attributes */
  1138. DEFINE_IPL_ATTR_RW(dump_ccw, device, "0.0.%04llx\n", "0.0.%llx\n",
  1139. dump_block_ccw->ipl_info.ccw.devno);
  1140. static struct attribute *dump_ccw_attrs[] = {
  1141. &sys_dump_ccw_device_attr.attr,
  1142. NULL,
  1143. };
  1144. static struct attribute_group dump_ccw_attr_group = {
  1145. .name = IPL_CCW_STR,
  1146. .attrs = dump_ccw_attrs,
  1147. };
  1148. /* dump type */
  1149. static int dump_set_type(enum dump_type type)
  1150. {
  1151. if (!(dump_capabilities & type))
  1152. return -EINVAL;
  1153. switch (type) {
  1154. case DUMP_TYPE_CCW:
  1155. if (diag308_set_works)
  1156. dump_method = DUMP_METHOD_CCW_DIAG;
  1157. else if (MACHINE_IS_VM)
  1158. dump_method = DUMP_METHOD_CCW_VM;
  1159. else
  1160. dump_method = DUMP_METHOD_CCW_CIO;
  1161. break;
  1162. case DUMP_TYPE_FCP:
  1163. dump_method = DUMP_METHOD_FCP_DIAG;
  1164. break;
  1165. default:
  1166. dump_method = DUMP_METHOD_NONE;
  1167. }
  1168. dump_type = type;
  1169. return 0;
  1170. }
  1171. static ssize_t dump_type_show(struct kobject *kobj,
  1172. struct kobj_attribute *attr, char *page)
  1173. {
  1174. return sprintf(page, "%s\n", dump_type_str(dump_type));
  1175. }
  1176. static ssize_t dump_type_store(struct kobject *kobj,
  1177. struct kobj_attribute *attr,
  1178. const char *buf, size_t len)
  1179. {
  1180. int rc = -EINVAL;
  1181. if (strncmp(buf, DUMP_NONE_STR, strlen(DUMP_NONE_STR)) == 0)
  1182. rc = dump_set_type(DUMP_TYPE_NONE);
  1183. else if (strncmp(buf, DUMP_CCW_STR, strlen(DUMP_CCW_STR)) == 0)
  1184. rc = dump_set_type(DUMP_TYPE_CCW);
  1185. else if (strncmp(buf, DUMP_FCP_STR, strlen(DUMP_FCP_STR)) == 0)
  1186. rc = dump_set_type(DUMP_TYPE_FCP);
  1187. return (rc != 0) ? rc : len;
  1188. }
  1189. static struct kobj_attribute dump_type_attr =
  1190. __ATTR(dump_type, 0644, dump_type_show, dump_type_store);
  1191. static struct kset *dump_kset;
  1192. static void diag308_dump(void *dump_block)
  1193. {
  1194. diag308(DIAG308_SET, dump_block);
  1195. while (1) {
  1196. if (diag308(DIAG308_DUMP, NULL) != 0x302)
  1197. break;
  1198. udelay_simple(USEC_PER_SEC);
  1199. }
  1200. }
  1201. static void __dump_run(void *unused)
  1202. {
  1203. struct ccw_dev_id devid;
  1204. static char buf[100];
  1205. switch (dump_method) {
  1206. case DUMP_METHOD_CCW_CIO:
  1207. devid.devno = dump_block_ccw->ipl_info.ccw.devno;
  1208. devid.ssid = 0;
  1209. reipl_ccw_dev(&devid);
  1210. break;
  1211. case DUMP_METHOD_CCW_VM:
  1212. sprintf(buf, "STORE STATUS");
  1213. __cpcmd(buf, NULL, 0, NULL);
  1214. sprintf(buf, "IPL %X", dump_block_ccw->ipl_info.ccw.devno);
  1215. __cpcmd(buf, NULL, 0, NULL);
  1216. break;
  1217. case DUMP_METHOD_CCW_DIAG:
  1218. diag308_dump(dump_block_ccw);
  1219. break;
  1220. case DUMP_METHOD_FCP_DIAG:
  1221. diag308_dump(dump_block_fcp);
  1222. break;
  1223. default:
  1224. break;
  1225. }
  1226. }
  1227. static void dump_run(struct shutdown_trigger *trigger)
  1228. {
  1229. if (dump_method == DUMP_METHOD_NONE)
  1230. return;
  1231. smp_send_stop();
  1232. smp_call_ipl_cpu(__dump_run, NULL);
  1233. }
  1234. static int __init dump_ccw_init(void)
  1235. {
  1236. int rc;
  1237. dump_block_ccw = (void *) get_zeroed_page(GFP_KERNEL);
  1238. if (!dump_block_ccw)
  1239. return -ENOMEM;
  1240. rc = sysfs_create_group(&dump_kset->kobj, &dump_ccw_attr_group);
  1241. if (rc) {
  1242. free_page((unsigned long)dump_block_ccw);
  1243. return rc;
  1244. }
  1245. dump_block_ccw->hdr.len = IPL_PARM_BLK_CCW_LEN;
  1246. dump_block_ccw->hdr.version = IPL_PARM_BLOCK_VERSION;
  1247. dump_block_ccw->hdr.blk0_len = IPL_PARM_BLK0_CCW_LEN;
  1248. dump_block_ccw->hdr.pbt = DIAG308_IPL_TYPE_CCW;
  1249. dump_capabilities |= DUMP_TYPE_CCW;
  1250. return 0;
  1251. }
  1252. static int __init dump_fcp_init(void)
  1253. {
  1254. int rc;
  1255. if (!sclp_ipl_info.has_dump)
  1256. return 0; /* LDIPL DUMP is not installed */
  1257. if (!diag308_set_works)
  1258. return 0;
  1259. dump_block_fcp = (void *) get_zeroed_page(GFP_KERNEL);
  1260. if (!dump_block_fcp)
  1261. return -ENOMEM;
  1262. rc = sysfs_create_group(&dump_kset->kobj, &dump_fcp_attr_group);
  1263. if (rc) {
  1264. free_page((unsigned long)dump_block_fcp);
  1265. return rc;
  1266. }
  1267. dump_block_fcp->hdr.len = IPL_PARM_BLK_FCP_LEN;
  1268. dump_block_fcp->hdr.version = IPL_PARM_BLOCK_VERSION;
  1269. dump_block_fcp->hdr.blk0_len = IPL_PARM_BLK0_FCP_LEN;
  1270. dump_block_fcp->hdr.pbt = DIAG308_IPL_TYPE_FCP;
  1271. dump_block_fcp->ipl_info.fcp.opt = DIAG308_IPL_OPT_DUMP;
  1272. dump_capabilities |= DUMP_TYPE_FCP;
  1273. return 0;
  1274. }
  1275. static int __init dump_init(void)
  1276. {
  1277. int rc;
  1278. dump_kset = kset_create_and_add("dump", NULL, firmware_kobj);
  1279. if (!dump_kset)
  1280. return -ENOMEM;
  1281. rc = sysfs_create_file(&dump_kset->kobj, &dump_type_attr.attr);
  1282. if (rc) {
  1283. kset_unregister(dump_kset);
  1284. return rc;
  1285. }
  1286. rc = dump_ccw_init();
  1287. if (rc)
  1288. return rc;
  1289. rc = dump_fcp_init();
  1290. if (rc)
  1291. return rc;
  1292. dump_set_type(DUMP_TYPE_NONE);
  1293. return 0;
  1294. }
  1295. static struct shutdown_action __refdata dump_action = {
  1296. .name = SHUTDOWN_ACTION_DUMP_STR,
  1297. .fn = dump_run,
  1298. .init = dump_init,
  1299. };
  1300. static void dump_reipl_run(struct shutdown_trigger *trigger)
  1301. {
  1302. unsigned long ipib = (unsigned long) reipl_block_actual;
  1303. unsigned int csum;
  1304. csum = csum_partial(reipl_block_actual, reipl_block_actual->hdr.len, 0);
  1305. mem_assign_absolute(S390_lowcore.ipib, ipib);
  1306. mem_assign_absolute(S390_lowcore.ipib_checksum, csum);
  1307. dump_run(trigger);
  1308. }
  1309. static int __init dump_reipl_init(void)
  1310. {
  1311. if (!diag308_set_works)
  1312. return -EOPNOTSUPP;
  1313. else
  1314. return 0;
  1315. }
  1316. static struct shutdown_action __refdata dump_reipl_action = {
  1317. .name = SHUTDOWN_ACTION_DUMP_REIPL_STR,
  1318. .fn = dump_reipl_run,
  1319. .init = dump_reipl_init,
  1320. };
  1321. /*
  1322. * vmcmd shutdown action: Trigger vm command on shutdown.
  1323. */
  1324. static char vmcmd_on_reboot[128];
  1325. static char vmcmd_on_panic[128];
  1326. static char vmcmd_on_halt[128];
  1327. static char vmcmd_on_poff[128];
  1328. static char vmcmd_on_restart[128];
  1329. DEFINE_IPL_ATTR_STR_RW(vmcmd, on_reboot, "%s\n", "%s\n", vmcmd_on_reboot);
  1330. DEFINE_IPL_ATTR_STR_RW(vmcmd, on_panic, "%s\n", "%s\n", vmcmd_on_panic);
  1331. DEFINE_IPL_ATTR_STR_RW(vmcmd, on_halt, "%s\n", "%s\n", vmcmd_on_halt);
  1332. DEFINE_IPL_ATTR_STR_RW(vmcmd, on_poff, "%s\n", "%s\n", vmcmd_on_poff);
  1333. DEFINE_IPL_ATTR_STR_RW(vmcmd, on_restart, "%s\n", "%s\n", vmcmd_on_restart);
  1334. static struct attribute *vmcmd_attrs[] = {
  1335. &sys_vmcmd_on_reboot_attr.attr,
  1336. &sys_vmcmd_on_panic_attr.attr,
  1337. &sys_vmcmd_on_halt_attr.attr,
  1338. &sys_vmcmd_on_poff_attr.attr,
  1339. &sys_vmcmd_on_restart_attr.attr,
  1340. NULL,
  1341. };
  1342. static struct attribute_group vmcmd_attr_group = {
  1343. .attrs = vmcmd_attrs,
  1344. };
  1345. static struct kset *vmcmd_kset;
  1346. static void vmcmd_run(struct shutdown_trigger *trigger)
  1347. {
  1348. char *cmd;
  1349. if (strcmp(trigger->name, ON_REIPL_STR) == 0)
  1350. cmd = vmcmd_on_reboot;
  1351. else if (strcmp(trigger->name, ON_PANIC_STR) == 0)
  1352. cmd = vmcmd_on_panic;
  1353. else if (strcmp(trigger->name, ON_HALT_STR) == 0)
  1354. cmd = vmcmd_on_halt;
  1355. else if (strcmp(trigger->name, ON_POFF_STR) == 0)
  1356. cmd = vmcmd_on_poff;
  1357. else if (strcmp(trigger->name, ON_RESTART_STR) == 0)
  1358. cmd = vmcmd_on_restart;
  1359. else
  1360. return;
  1361. if (strlen(cmd) == 0)
  1362. return;
  1363. __cpcmd(cmd, NULL, 0, NULL);
  1364. }
  1365. static int vmcmd_init(void)
  1366. {
  1367. if (!MACHINE_IS_VM)
  1368. return -EOPNOTSUPP;
  1369. vmcmd_kset = kset_create_and_add("vmcmd", NULL, firmware_kobj);
  1370. if (!vmcmd_kset)
  1371. return -ENOMEM;
  1372. return sysfs_create_group(&vmcmd_kset->kobj, &vmcmd_attr_group);
  1373. }
  1374. static struct shutdown_action vmcmd_action = {SHUTDOWN_ACTION_VMCMD_STR,
  1375. vmcmd_run, vmcmd_init};
  1376. /*
  1377. * stop shutdown action: Stop Linux on shutdown.
  1378. */
  1379. static void stop_run(struct shutdown_trigger *trigger)
  1380. {
  1381. if (strcmp(trigger->name, ON_PANIC_STR) == 0 ||
  1382. strcmp(trigger->name, ON_RESTART_STR) == 0)
  1383. disabled_wait((unsigned long) __builtin_return_address(0));
  1384. smp_stop_cpu();
  1385. }
  1386. static struct shutdown_action stop_action = {SHUTDOWN_ACTION_STOP_STR,
  1387. stop_run, NULL};
  1388. /* action list */
  1389. static struct shutdown_action *shutdown_actions_list[] = {
  1390. &ipl_action, &reipl_action, &dump_reipl_action, &dump_action,
  1391. &vmcmd_action, &stop_action};
  1392. #define SHUTDOWN_ACTIONS_COUNT (sizeof(shutdown_actions_list) / sizeof(void *))
  1393. /*
  1394. * Trigger section
  1395. */
  1396. static struct kset *shutdown_actions_kset;
  1397. static int set_trigger(const char *buf, struct shutdown_trigger *trigger,
  1398. size_t len)
  1399. {
  1400. int i;
  1401. for (i = 0; i < SHUTDOWN_ACTIONS_COUNT; i++) {
  1402. if (sysfs_streq(buf, shutdown_actions_list[i]->name)) {
  1403. if (shutdown_actions_list[i]->init_rc) {
  1404. return shutdown_actions_list[i]->init_rc;
  1405. } else {
  1406. trigger->action = shutdown_actions_list[i];
  1407. return len;
  1408. }
  1409. }
  1410. }
  1411. return -EINVAL;
  1412. }
  1413. /* on reipl */
  1414. static struct shutdown_trigger on_reboot_trigger = {ON_REIPL_STR,
  1415. &reipl_action};
  1416. static ssize_t on_reboot_show(struct kobject *kobj,
  1417. struct kobj_attribute *attr, char *page)
  1418. {
  1419. return sprintf(page, "%s\n", on_reboot_trigger.action->name);
  1420. }
  1421. static ssize_t on_reboot_store(struct kobject *kobj,
  1422. struct kobj_attribute *attr,
  1423. const char *buf, size_t len)
  1424. {
  1425. return set_trigger(buf, &on_reboot_trigger, len);
  1426. }
  1427. static struct kobj_attribute on_reboot_attr = __ATTR_RW(on_reboot);
  1428. static void do_machine_restart(char *__unused)
  1429. {
  1430. smp_send_stop();
  1431. on_reboot_trigger.action->fn(&on_reboot_trigger);
  1432. reipl_run(NULL);
  1433. }
  1434. void (*_machine_restart)(char *command) = do_machine_restart;
  1435. /* on panic */
  1436. static struct shutdown_trigger on_panic_trigger = {ON_PANIC_STR, &stop_action};
  1437. static ssize_t on_panic_show(struct kobject *kobj,
  1438. struct kobj_attribute *attr, char *page)
  1439. {
  1440. return sprintf(page, "%s\n", on_panic_trigger.action->name);
  1441. }
  1442. static ssize_t on_panic_store(struct kobject *kobj,
  1443. struct kobj_attribute *attr,
  1444. const char *buf, size_t len)
  1445. {
  1446. return set_trigger(buf, &on_panic_trigger, len);
  1447. }
  1448. static struct kobj_attribute on_panic_attr = __ATTR_RW(on_panic);
  1449. static void do_panic(void)
  1450. {
  1451. lgr_info_log();
  1452. on_panic_trigger.action->fn(&on_panic_trigger);
  1453. stop_run(&on_panic_trigger);
  1454. }
  1455. /* on restart */
  1456. static struct shutdown_trigger on_restart_trigger = {ON_RESTART_STR,
  1457. &stop_action};
  1458. static ssize_t on_restart_show(struct kobject *kobj,
  1459. struct kobj_attribute *attr, char *page)
  1460. {
  1461. return sprintf(page, "%s\n", on_restart_trigger.action->name);
  1462. }
  1463. static ssize_t on_restart_store(struct kobject *kobj,
  1464. struct kobj_attribute *attr,
  1465. const char *buf, size_t len)
  1466. {
  1467. return set_trigger(buf, &on_restart_trigger, len);
  1468. }
  1469. static struct kobj_attribute on_restart_attr = __ATTR_RW(on_restart);
  1470. static void __do_restart(void *ignore)
  1471. {
  1472. __arch_local_irq_stosm(0x04); /* enable DAT */
  1473. smp_send_stop();
  1474. #ifdef CONFIG_CRASH_DUMP
  1475. crash_kexec(NULL);
  1476. #endif
  1477. on_restart_trigger.action->fn(&on_restart_trigger);
  1478. stop_run(&on_restart_trigger);
  1479. }
  1480. void do_restart(void)
  1481. {
  1482. tracing_off();
  1483. debug_locks_off();
  1484. lgr_info_log();
  1485. smp_call_online_cpu(__do_restart, NULL);
  1486. }
  1487. /* on halt */
  1488. static struct shutdown_trigger on_halt_trigger = {ON_HALT_STR, &stop_action};
  1489. static ssize_t on_halt_show(struct kobject *kobj,
  1490. struct kobj_attribute *attr, char *page)
  1491. {
  1492. return sprintf(page, "%s\n", on_halt_trigger.action->name);
  1493. }
  1494. static ssize_t on_halt_store(struct kobject *kobj,
  1495. struct kobj_attribute *attr,
  1496. const char *buf, size_t len)
  1497. {
  1498. return set_trigger(buf, &on_halt_trigger, len);
  1499. }
  1500. static struct kobj_attribute on_halt_attr = __ATTR_RW(on_halt);
  1501. static void do_machine_halt(void)
  1502. {
  1503. smp_send_stop();
  1504. on_halt_trigger.action->fn(&on_halt_trigger);
  1505. stop_run(&on_halt_trigger);
  1506. }
  1507. void (*_machine_halt)(void) = do_machine_halt;
  1508. /* on power off */
  1509. static struct shutdown_trigger on_poff_trigger = {ON_POFF_STR, &stop_action};
  1510. static ssize_t on_poff_show(struct kobject *kobj,
  1511. struct kobj_attribute *attr, char *page)
  1512. {
  1513. return sprintf(page, "%s\n", on_poff_trigger.action->name);
  1514. }
  1515. static ssize_t on_poff_store(struct kobject *kobj,
  1516. struct kobj_attribute *attr,
  1517. const char *buf, size_t len)
  1518. {
  1519. return set_trigger(buf, &on_poff_trigger, len);
  1520. }
  1521. static struct kobj_attribute on_poff_attr = __ATTR_RW(on_poff);
  1522. static void do_machine_power_off(void)
  1523. {
  1524. smp_send_stop();
  1525. on_poff_trigger.action->fn(&on_poff_trigger);
  1526. stop_run(&on_poff_trigger);
  1527. }
  1528. void (*_machine_power_off)(void) = do_machine_power_off;
  1529. static struct attribute *shutdown_action_attrs[] = {
  1530. &on_restart_attr.attr,
  1531. &on_reboot_attr.attr,
  1532. &on_panic_attr.attr,
  1533. &on_halt_attr.attr,
  1534. &on_poff_attr.attr,
  1535. NULL,
  1536. };
  1537. static struct attribute_group shutdown_action_attr_group = {
  1538. .attrs = shutdown_action_attrs,
  1539. };
  1540. static void __init shutdown_triggers_init(void)
  1541. {
  1542. shutdown_actions_kset = kset_create_and_add("shutdown_actions", NULL,
  1543. firmware_kobj);
  1544. if (!shutdown_actions_kset)
  1545. goto fail;
  1546. if (sysfs_create_group(&shutdown_actions_kset->kobj,
  1547. &shutdown_action_attr_group))
  1548. goto fail;
  1549. return;
  1550. fail:
  1551. panic("shutdown_triggers_init failed\n");
  1552. }
  1553. static void __init shutdown_actions_init(void)
  1554. {
  1555. int i;
  1556. for (i = 0; i < SHUTDOWN_ACTIONS_COUNT; i++) {
  1557. if (!shutdown_actions_list[i]->init)
  1558. continue;
  1559. shutdown_actions_list[i]->init_rc =
  1560. shutdown_actions_list[i]->init();
  1561. }
  1562. }
  1563. static int __init s390_ipl_init(void)
  1564. {
  1565. char str[8] = {0x40, 0x40, 0x40, 0x40, 0x40, 0x40, 0x40, 0x40};
  1566. sclp_get_ipl_info(&sclp_ipl_info);
  1567. /*
  1568. * Fix loadparm: There are systems where the (SCSI) LOADPARM
  1569. * returned by read SCP info is invalid (contains EBCDIC blanks)
  1570. * when the system has been booted via diag308. In that case we use
  1571. * the value from diag308, if available.
  1572. *
  1573. * There are also systems where diag308 store does not work in
  1574. * case the system is booted from HMC. Fortunately in this case
  1575. * READ SCP info provides the correct value.
  1576. */
  1577. if (memcmp(sclp_ipl_info.loadparm, str, sizeof(str)) == 0 &&
  1578. diag308_set_works)
  1579. memcpy(sclp_ipl_info.loadparm, ipl_block.hdr.loadparm,
  1580. LOADPARM_LEN);
  1581. shutdown_actions_init();
  1582. shutdown_triggers_init();
  1583. return 0;
  1584. }
  1585. __initcall(s390_ipl_init);
  1586. static void __init strncpy_skip_quote(char *dst, char *src, int n)
  1587. {
  1588. int sx, dx;
  1589. dx = 0;
  1590. for (sx = 0; src[sx] != 0; sx++) {
  1591. if (src[sx] == '"')
  1592. continue;
  1593. dst[dx++] = src[sx];
  1594. if (dx >= n)
  1595. break;
  1596. }
  1597. }
  1598. static int __init vmcmd_on_reboot_setup(char *str)
  1599. {
  1600. if (!MACHINE_IS_VM)
  1601. return 1;
  1602. strncpy_skip_quote(vmcmd_on_reboot, str, 127);
  1603. vmcmd_on_reboot[127] = 0;
  1604. on_reboot_trigger.action = &vmcmd_action;
  1605. return 1;
  1606. }
  1607. __setup("vmreboot=", vmcmd_on_reboot_setup);
  1608. static int __init vmcmd_on_panic_setup(char *str)
  1609. {
  1610. if (!MACHINE_IS_VM)
  1611. return 1;
  1612. strncpy_skip_quote(vmcmd_on_panic, str, 127);
  1613. vmcmd_on_panic[127] = 0;
  1614. on_panic_trigger.action = &vmcmd_action;
  1615. return 1;
  1616. }
  1617. __setup("vmpanic=", vmcmd_on_panic_setup);
  1618. static int __init vmcmd_on_halt_setup(char *str)
  1619. {
  1620. if (!MACHINE_IS_VM)
  1621. return 1;
  1622. strncpy_skip_quote(vmcmd_on_halt, str, 127);
  1623. vmcmd_on_halt[127] = 0;
  1624. on_halt_trigger.action = &vmcmd_action;
  1625. return 1;
  1626. }
  1627. __setup("vmhalt=", vmcmd_on_halt_setup);
  1628. static int __init vmcmd_on_poff_setup(char *str)
  1629. {
  1630. if (!MACHINE_IS_VM)
  1631. return 1;
  1632. strncpy_skip_quote(vmcmd_on_poff, str, 127);
  1633. vmcmd_on_poff[127] = 0;
  1634. on_poff_trigger.action = &vmcmd_action;
  1635. return 1;
  1636. }
  1637. __setup("vmpoff=", vmcmd_on_poff_setup);
  1638. static int on_panic_notify(struct notifier_block *self,
  1639. unsigned long event, void *data)
  1640. {
  1641. do_panic();
  1642. return NOTIFY_OK;
  1643. }
  1644. static struct notifier_block on_panic_nb = {
  1645. .notifier_call = on_panic_notify,
  1646. .priority = INT_MIN,
  1647. };
  1648. void __init setup_ipl(void)
  1649. {
  1650. ipl_info.type = get_ipl_type();
  1651. switch (ipl_info.type) {
  1652. case IPL_TYPE_CCW:
  1653. ipl_info.data.ccw.dev_id.devno = ipl_devno;
  1654. ipl_info.data.ccw.dev_id.ssid = 0;
  1655. break;
  1656. case IPL_TYPE_FCP:
  1657. case IPL_TYPE_FCP_DUMP:
  1658. ipl_info.data.fcp.dev_id.devno =
  1659. IPL_PARMBLOCK_START->ipl_info.fcp.devno;
  1660. ipl_info.data.fcp.dev_id.ssid = 0;
  1661. ipl_info.data.fcp.wwpn = IPL_PARMBLOCK_START->ipl_info.fcp.wwpn;
  1662. ipl_info.data.fcp.lun = IPL_PARMBLOCK_START->ipl_info.fcp.lun;
  1663. break;
  1664. case IPL_TYPE_NSS:
  1665. strncpy(ipl_info.data.nss.name, kernel_nss_name,
  1666. sizeof(ipl_info.data.nss.name));
  1667. break;
  1668. case IPL_TYPE_UNKNOWN:
  1669. /* We have no info to copy */
  1670. break;
  1671. }
  1672. atomic_notifier_chain_register(&panic_notifier_list, &on_panic_nb);
  1673. }
  1674. void __init ipl_update_parameters(void)
  1675. {
  1676. int rc;
  1677. rc = diag308(DIAG308_STORE, &ipl_block);
  1678. if ((rc == DIAG308_RC_OK) || (rc == DIAG308_RC_NOCONFIG))
  1679. diag308_set_works = 1;
  1680. }
  1681. void __init ipl_save_parameters(void)
  1682. {
  1683. struct cio_iplinfo iplinfo;
  1684. void *src, *dst;
  1685. if (cio_get_iplinfo(&iplinfo))
  1686. return;
  1687. ipl_devno = iplinfo.devno;
  1688. ipl_flags |= IPL_DEVNO_VALID;
  1689. if (!iplinfo.is_qdio)
  1690. return;
  1691. ipl_flags |= IPL_PARMBLOCK_VALID;
  1692. src = (void *)(unsigned long)S390_lowcore.ipl_parmblock_ptr;
  1693. dst = (void *)IPL_PARMBLOCK_ORIGIN;
  1694. memmove(dst, src, PAGE_SIZE);
  1695. S390_lowcore.ipl_parmblock_ptr = IPL_PARMBLOCK_ORIGIN;
  1696. }
  1697. static LIST_HEAD(rcall);
  1698. static DEFINE_MUTEX(rcall_mutex);
  1699. void register_reset_call(struct reset_call *reset)
  1700. {
  1701. mutex_lock(&rcall_mutex);
  1702. list_add(&reset->list, &rcall);
  1703. mutex_unlock(&rcall_mutex);
  1704. }
  1705. EXPORT_SYMBOL_GPL(register_reset_call);
  1706. void unregister_reset_call(struct reset_call *reset)
  1707. {
  1708. mutex_lock(&rcall_mutex);
  1709. list_del(&reset->list);
  1710. mutex_unlock(&rcall_mutex);
  1711. }
  1712. EXPORT_SYMBOL_GPL(unregister_reset_call);
  1713. static void do_reset_calls(void)
  1714. {
  1715. struct reset_call *reset;
  1716. if (diag308_set_works) {
  1717. diag308_reset();
  1718. return;
  1719. }
  1720. list_for_each_entry(reset, &rcall, list)
  1721. reset->fn();
  1722. }
  1723. u32 dump_prefix_page;
  1724. void s390_reset_system(void (*fn_pre)(void),
  1725. void (*fn_post)(void *), void *data)
  1726. {
  1727. struct _lowcore *lc;
  1728. lc = (struct _lowcore *)(unsigned long) store_prefix();
  1729. /* Stack for interrupt/machine check handler */
  1730. lc->panic_stack = S390_lowcore.panic_stack;
  1731. /* Save prefix page address for dump case */
  1732. dump_prefix_page = (u32)(unsigned long) lc;
  1733. /* Disable prefixing */
  1734. set_prefix(0);
  1735. /* Disable lowcore protection */
  1736. __ctl_clear_bit(0,28);
  1737. /* Set new machine check handler */
  1738. S390_lowcore.mcck_new_psw.mask = PSW_KERNEL_BITS | PSW_MASK_DAT;
  1739. S390_lowcore.mcck_new_psw.addr =
  1740. PSW_ADDR_AMODE | (unsigned long) s390_base_mcck_handler;
  1741. /* Set new program check handler */
  1742. S390_lowcore.program_new_psw.mask = PSW_KERNEL_BITS | PSW_MASK_DAT;
  1743. S390_lowcore.program_new_psw.addr =
  1744. PSW_ADDR_AMODE | (unsigned long) s390_base_pgm_handler;
  1745. /*
  1746. * Clear subchannel ID and number to signal new kernel that no CCW or
  1747. * SCSI IPL has been done (for kexec and kdump)
  1748. */
  1749. S390_lowcore.subchannel_id = 0;
  1750. S390_lowcore.subchannel_nr = 0;
  1751. /* Store status at absolute zero */
  1752. store_status();
  1753. /* Call function before reset */
  1754. if (fn_pre)
  1755. fn_pre();
  1756. do_reset_calls();
  1757. /* Call function after reset */
  1758. if (fn_post)
  1759. fn_post(data);
  1760. }