PageRenderTime 45ms CodeModel.GetById 9ms RepoModel.GetById 0ms app.codeStats 0ms

/src/sview/part_info.c

https://github.com/cfenoy/slurm
C | 3056 lines | 2691 code | 257 blank | 108 comment | 527 complexity | 2a273b760446c62347919e7a7a07d294 MD5 | raw file
Possible License(s): GPL-2.0, AGPL-1.0
  1. /*****************************************************************************\
  2. * part_info.c - Functions related to partition display
  3. * mode of sview.
  4. *****************************************************************************
  5. * Copyright (C) 2004-2007 The Regents of the University of California.
  6. * Copyright (C) 2008-2010 Lawrence Livermore National Security.
  7. * Portions Copyright (C) 2010 SchedMD <http://www.schedmd.com>.
  8. * Produced at Lawrence Livermore National Laboratory (cf, DISCLAIMER).
  9. * Written by Danny Auble <da@llnl.gov>
  10. *
  11. * CODE-OCEC-09-009. All rights reserved.
  12. *
  13. * This file is part of SLURM, a resource management program.
  14. * For details, see <http://www.schedmd.com/slurmdocs/>.
  15. * Please also read the included file: DISCLAIMER.
  16. *
  17. * SLURM is free software; you can redistribute it and/or modify it under
  18. * the terms of the GNU General Public License as published by the Free
  19. * Software Foundation; either version 2 of the License, or (at your option)
  20. * any later version.
  21. *
  22. * SLURM is distributed in the hope that it will be useful, but WITHOUT ANY
  23. * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
  24. * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
  25. * details.
  26. *
  27. * You should have received a copy of the GNU General Public License along
  28. * with SLURM; if not, write to the Free Software Foundation, Inc.,
  29. * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
  30. \*****************************************************************************/
  31. #include "src/sview/sview.h"
  32. #include "src/common/parse_time.h"
  33. #include <grp.h>
  34. #define _DEBUG 0
  35. static GtkListStore *_create_model_part2(int type);
  36. typedef struct {
  37. uint32_t cpu_alloc_cnt;
  38. uint32_t cpu_error_cnt;
  39. uint32_t cpu_idle_cnt;
  40. uint32_t disk_total;
  41. char *features;
  42. hostlist_t hl;
  43. uint32_t mem_total;
  44. uint32_t node_cnt;
  45. List node_ptr_list;
  46. uint16_t node_state;
  47. partition_info_t* part_ptr;
  48. char *reason;
  49. } sview_part_sub_t;
  50. /* Collection of data for printing reports. Like data is combined here */
  51. typedef struct {
  52. int color_inx;
  53. GtkTreeIter iter_ptr;
  54. bool iter_set;
  55. /* part_info contains partition, avail, max_time, job_size,
  56. * root, share, groups */
  57. partition_info_t* part_ptr;
  58. int pos;
  59. List sub_list;
  60. sview_part_sub_t sub_part_total;
  61. } sview_part_info_t;
  62. enum {
  63. EDIT_PART_STATE = 1,
  64. EDIT_REMOVE_PART,
  65. EDIT_EDIT
  66. };
  67. /* These need to be in alpha order (except POS and CNT) */
  68. enum {
  69. SORTID_POS = POS_LOC,
  70. SORTID_ALTERNATE,
  71. SORTID_COLOR,
  72. SORTID_COLOR_INX,
  73. SORTID_CPUS,
  74. SORTID_DEFAULT,
  75. SORTID_FEATURES,
  76. SORTID_GRACE_TIME,
  77. SORTID_GROUPS,
  78. SORTID_HIDDEN,
  79. SORTID_JOB_SIZE,
  80. SORTID_MEM,
  81. #ifdef HAVE_BG
  82. SORTID_NODELIST,
  83. SORTID_NODES_ALLOWED,
  84. #endif
  85. SORTID_NAME,
  86. #ifndef HAVE_BG
  87. SORTID_NODELIST,
  88. SORTID_NODES_ALLOWED,
  89. #endif
  90. SORTID_NODE_INX,
  91. SORTID_NODE_STATE,
  92. SORTID_NODE_STATE_NUM,
  93. SORTID_NODES,
  94. SORTID_NODES_MAX,
  95. SORTID_NODES_MIN,
  96. SORTID_ONLY_LINE,
  97. SORTID_PART_STATE,
  98. SORTID_PREEMPT_MODE,
  99. SORTID_PRIORITY,
  100. SORTID_REASON,
  101. SORTID_ROOT,
  102. SORTID_SHARE,
  103. SORTID_TMP_DISK,
  104. SORTID_TIMELIMIT,
  105. SORTID_UPDATED,
  106. SORTID_CNT
  107. };
  108. /*these are the settings to apply for the user
  109. * on the first startup after a fresh slurm install.*/
  110. static char *_initial_page_opts = "Partition,Default,Part_State,"
  111. "Time_Limit,Node_Count,Node_State,NodeList";
  112. static display_data_t display_data_part[] = {
  113. {G_TYPE_INT, SORTID_POS, NULL, FALSE, EDIT_NONE, refresh_part},
  114. {G_TYPE_STRING, SORTID_NAME, "Partition", FALSE,
  115. EDIT_NONE, refresh_part, create_model_part, admin_edit_part},
  116. {G_TYPE_STRING, SORTID_COLOR, NULL, TRUE, EDIT_COLOR, refresh_part,
  117. create_model_part, admin_edit_part},
  118. {G_TYPE_STRING, SORTID_ALTERNATE, "Alternate", FALSE,
  119. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  120. {G_TYPE_STRING, SORTID_DEFAULT, "Default", FALSE,
  121. EDIT_MODEL, refresh_part, create_model_part, admin_edit_part},
  122. {G_TYPE_STRING, SORTID_GRACE_TIME, "GraceTime", FALSE,
  123. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  124. {G_TYPE_STRING, SORTID_HIDDEN, "Hidden", FALSE,
  125. EDIT_MODEL, refresh_part, create_model_part, admin_edit_part},
  126. {G_TYPE_STRING, SORTID_PART_STATE, "Part State", FALSE,
  127. EDIT_MODEL, refresh_part, create_model_part, admin_edit_part},
  128. {G_TYPE_STRING, SORTID_TIMELIMIT, "Time Limit", FALSE,
  129. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  130. {G_TYPE_STRING, SORTID_NODES, "Node Count", FALSE,
  131. EDIT_NONE, refresh_part, create_model_part, admin_edit_part},
  132. {G_TYPE_STRING, SORTID_CPUS, "CPU Count", FALSE,
  133. EDIT_NONE, refresh_part, create_model_part, admin_edit_part},
  134. {G_TYPE_STRING, SORTID_NODE_STATE, "Node State", FALSE,
  135. EDIT_MODEL, refresh_part,
  136. create_model_part, admin_edit_part},
  137. {G_TYPE_STRING, SORTID_JOB_SIZE, "Job Size", FALSE,
  138. EDIT_NONE, refresh_part, create_model_part, admin_edit_part},
  139. {G_TYPE_STRING, SORTID_PREEMPT_MODE, "PreemptMode", FALSE,
  140. EDIT_MODEL, refresh_part, create_model_part, admin_edit_part},
  141. {G_TYPE_STRING, SORTID_PRIORITY, "Priority", FALSE,
  142. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  143. {G_TYPE_STRING, SORTID_NODES_MIN, "Nodes Min", FALSE,
  144. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  145. {G_TYPE_STRING, SORTID_NODES_MAX, "Nodes Max", FALSE,
  146. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  147. {G_TYPE_STRING, SORTID_ROOT, "Root", FALSE, EDIT_MODEL, refresh_part,
  148. create_model_part, admin_edit_part},
  149. {G_TYPE_STRING, SORTID_SHARE, "Share", FALSE, EDIT_MODEL, refresh_part,
  150. create_model_part, admin_edit_part},
  151. {G_TYPE_STRING, SORTID_GROUPS, "Groups Allowed", FALSE,
  152. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  153. {G_TYPE_STRING, SORTID_NODES_ALLOWED, "Nodes Allowed Allocating", FALSE,
  154. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  155. {G_TYPE_STRING, SORTID_TMP_DISK, "Temp Disk", FALSE,
  156. EDIT_NONE, refresh_part, create_model_part, admin_edit_part},
  157. {G_TYPE_STRING, SORTID_MEM, "Memory", FALSE, EDIT_NONE, refresh_part,
  158. create_model_part, admin_edit_part},
  159. {G_TYPE_STRING, SORTID_FEATURES, "Features", FALSE,
  160. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  161. {G_TYPE_STRING, SORTID_REASON, "Reason", FALSE,
  162. EDIT_NONE, refresh_part, create_model_part, admin_edit_part},
  163. #ifdef HAVE_BG
  164. {G_TYPE_STRING, SORTID_NODELIST, "MidplaneList", FALSE,
  165. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  166. #else
  167. {G_TYPE_STRING, SORTID_NODELIST, "NodeList", FALSE,
  168. EDIT_TEXTBOX, refresh_part, create_model_part, admin_edit_part},
  169. #endif
  170. {G_TYPE_INT, SORTID_NODE_STATE_NUM, NULL, FALSE,
  171. EDIT_NONE, refresh_part, create_model_part, admin_edit_part},
  172. {G_TYPE_INT, SORTID_ONLY_LINE, NULL, FALSE, EDIT_NONE, refresh_part,
  173. create_model_part, admin_edit_part},
  174. {G_TYPE_INT, SORTID_COLOR_INX, NULL, FALSE, EDIT_NONE, refresh_part,
  175. create_model_part, admin_edit_part},
  176. {G_TYPE_POINTER, SORTID_NODE_INX, NULL, FALSE, EDIT_NONE,
  177. refresh_part, create_model_part, admin_edit_part},
  178. {G_TYPE_INT, SORTID_UPDATED, NULL, FALSE, EDIT_NONE, refresh_part,
  179. create_model_part, admin_edit_part},
  180. {G_TYPE_NONE, -1, NULL, FALSE, EDIT_NONE}
  181. };
  182. static display_data_t create_data_part[] = {
  183. {G_TYPE_INT, SORTID_POS, NULL, FALSE, EDIT_NONE, refresh_part},
  184. {G_TYPE_STRING, SORTID_NAME, "Name", FALSE,
  185. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  186. {G_TYPE_STRING, SORTID_ALTERNATE, "Alternate", FALSE,
  187. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  188. {G_TYPE_STRING, SORTID_DEFAULT, "Default", FALSE,
  189. EDIT_MODEL, refresh_part, _create_model_part2, admin_edit_part},
  190. {G_TYPE_STRING, SORTID_GRACE_TIME, "GraceTime", FALSE,
  191. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  192. {G_TYPE_STRING, SORTID_HIDDEN, "Hidden", FALSE,
  193. EDIT_MODEL, refresh_part, _create_model_part2, admin_edit_part},
  194. {G_TYPE_STRING, SORTID_PART_STATE, "State", FALSE,
  195. EDIT_MODEL, refresh_part, _create_model_part2, admin_edit_part},
  196. {G_TYPE_STRING, SORTID_TIMELIMIT, "Time Limit", FALSE,
  197. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  198. {G_TYPE_STRING, SORTID_PREEMPT_MODE, "PreemptMode", FALSE,
  199. EDIT_MODEL, refresh_part, _create_model_part2, admin_edit_part},
  200. {G_TYPE_STRING, SORTID_PRIORITY, "Priority", FALSE,
  201. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  202. {G_TYPE_STRING, SORTID_NODES_MIN, "Nodes Min", FALSE,
  203. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  204. {G_TYPE_STRING, SORTID_NODES_MAX, "Nodes Max", FALSE,
  205. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  206. {G_TYPE_STRING, SORTID_ROOT, "Root", FALSE,
  207. EDIT_MODEL, refresh_part, _create_model_part2, admin_edit_part},
  208. {G_TYPE_STRING, SORTID_SHARE, "Share", FALSE,
  209. EDIT_MODEL, refresh_part, _create_model_part2, admin_edit_part},
  210. {G_TYPE_STRING, SORTID_GROUPS, "Groups Allowed", FALSE,
  211. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  212. {G_TYPE_STRING, SORTID_NODES_ALLOWED, "Nodes Allowed Allocating", FALSE,
  213. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  214. {G_TYPE_STRING, SORTID_FEATURES, "Features", FALSE,
  215. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  216. {G_TYPE_STRING, SORTID_REASON, "Reason", FALSE,
  217. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  218. #ifdef HAVE_BG
  219. {G_TYPE_STRING, SORTID_NODELIST, "MidplaneList", FALSE,
  220. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  221. #else
  222. {G_TYPE_STRING, SORTID_NODELIST, "NodeList", FALSE,
  223. EDIT_TEXTBOX, refresh_part, _create_model_part2, admin_edit_part},
  224. #endif
  225. {G_TYPE_NONE, -1, NULL, FALSE, EDIT_NONE}
  226. };
  227. static display_data_t options_data_part[] = {
  228. {G_TYPE_INT, SORTID_POS, NULL, FALSE, EDIT_NONE},
  229. {G_TYPE_STRING, INFO_PAGE, "Full Info", TRUE, PART_PAGE},
  230. {G_TYPE_STRING, PART_PAGE, "Edit Partition", TRUE, ADMIN_PAGE},
  231. {G_TYPE_STRING, PART_PAGE, "Remove Partition", TRUE, ADMIN_PAGE},
  232. #ifdef HAVE_BG
  233. {G_TYPE_STRING, PART_PAGE, "Drain Midplanes",
  234. TRUE, ADMIN_PAGE | EXTRA_NODES},
  235. {G_TYPE_STRING, PART_PAGE, "Resume Midplanes",
  236. TRUE, ADMIN_PAGE | EXTRA_NODES},
  237. {G_TYPE_STRING, PART_PAGE, "Put Midplanes Down",
  238. TRUE, ADMIN_PAGE | EXTRA_NODES},
  239. {G_TYPE_STRING, PART_PAGE, "Make Midplanes Idle",
  240. TRUE, ADMIN_PAGE | EXTRA_NODES},
  241. {G_TYPE_STRING, PART_PAGE, "Update Midplane Features",
  242. TRUE, ADMIN_PAGE | EXTRA_NODES},
  243. #else
  244. {G_TYPE_STRING, PART_PAGE, "Drain Nodes",
  245. TRUE, ADMIN_PAGE | EXTRA_NODES},
  246. {G_TYPE_STRING, PART_PAGE, "Resume Nodes",
  247. TRUE, ADMIN_PAGE | EXTRA_NODES},
  248. {G_TYPE_STRING, PART_PAGE, "Put Nodes Down",
  249. TRUE, ADMIN_PAGE | EXTRA_NODES},
  250. {G_TYPE_STRING, PART_PAGE, "Make Nodes Idle",
  251. TRUE, ADMIN_PAGE | EXTRA_NODES},
  252. {G_TYPE_STRING, PART_PAGE, "Update Node Features",
  253. TRUE, ADMIN_PAGE | EXTRA_NODES},
  254. #endif
  255. {G_TYPE_STRING, PART_PAGE, "Change Partition State",
  256. TRUE, ADMIN_PAGE},
  257. {G_TYPE_STRING, JOB_PAGE, "Jobs", TRUE, PART_PAGE},
  258. #ifdef HAVE_BG
  259. {G_TYPE_STRING, BLOCK_PAGE, "Blocks", TRUE, PART_PAGE},
  260. {G_TYPE_STRING, NODE_PAGE, "Midplanes", TRUE, PART_PAGE},
  261. #else
  262. {G_TYPE_STRING, BLOCK_PAGE, NULL, TRUE, PART_PAGE},
  263. {G_TYPE_STRING, NODE_PAGE, "Nodes", TRUE, PART_PAGE},
  264. #endif
  265. //{G_TYPE_STRING, SUBMIT_PAGE, "Job Submit", FALSE, PART_PAGE},
  266. {G_TYPE_STRING, RESV_PAGE, "Reservations", TRUE, PART_PAGE},
  267. {G_TYPE_NONE, -1, NULL, FALSE, EDIT_NONE}
  268. };
  269. static display_data_t *local_display_data = NULL;
  270. static char *got_edit_signal = NULL;
  271. static char *got_features_edit_signal = NULL;
  272. static void _append_part_sub_record(sview_part_sub_t *sview_part_sub,
  273. GtkTreeStore *treestore, GtkTreeIter *iter,
  274. int line);
  275. static void _update_part_sub_record(sview_part_sub_t *sview_part_sub,
  276. GtkTreeStore *treestore,
  277. GtkTreeIter *iter);
  278. static int _build_min_max_32_string(char *buffer, int buf_size,
  279. uint32_t min, uint32_t max, bool range)
  280. {
  281. char tmp_min[8];
  282. char tmp_max[8];
  283. convert_num_unit((float)min, tmp_min, sizeof(tmp_min), UNIT_NONE);
  284. convert_num_unit((float)max, tmp_max, sizeof(tmp_max), UNIT_NONE);
  285. if (max == min)
  286. return snprintf(buffer, buf_size, "%s", tmp_max);
  287. else if (range) {
  288. if (max == (uint32_t) INFINITE)
  289. return snprintf(buffer, buf_size, "%s-infinite",
  290. tmp_min);
  291. else
  292. return snprintf(buffer, buf_size, "%s-%s",
  293. tmp_min, tmp_max);
  294. } else
  295. return snprintf(buffer, buf_size, "%s+", tmp_min);
  296. }
  297. static void _set_active_combo_part(GtkComboBox *combo,
  298. GtkTreeModel *model, GtkTreeIter *iter,
  299. int type)
  300. {
  301. char *temp_char = NULL;
  302. int action = 0;
  303. int i = 0, unknown_found = 0;
  304. char *upper = NULL;
  305. if (model)
  306. gtk_tree_model_get(model, iter, type, &temp_char, -1);
  307. if (!temp_char)
  308. goto end_it;
  309. switch(type) {
  310. case SORTID_DEFAULT:
  311. case SORTID_HIDDEN:
  312. case SORTID_ROOT:
  313. if (!strcmp(temp_char, "yes"))
  314. action = 0;
  315. else if (!strcmp(temp_char, "no"))
  316. action = 1;
  317. else
  318. action = 0;
  319. break;
  320. case SORTID_SHARE:
  321. if (!strncmp(temp_char, "force", 5))
  322. action = 0;
  323. else if (!strcmp(temp_char, "no"))
  324. action = 1;
  325. else if (!strncmp(temp_char, "yes", 3))
  326. action = 2;
  327. else if (!strcmp(temp_char, "exclusive"))
  328. action = 3;
  329. else
  330. action = 0;
  331. break;
  332. case SORTID_PART_STATE:
  333. if (!strcmp(temp_char, "up"))
  334. action = 0;
  335. else if (!strcmp(temp_char, "down"))
  336. action = 1;
  337. else if (!strcmp(temp_char, "inactive"))
  338. action = 2;
  339. else if (!strcmp(temp_char, "drain"))
  340. action = 3;
  341. else
  342. action = 0;
  343. break;
  344. case SORTID_NODE_STATE:
  345. if (!strcasecmp(temp_char, "drain"))
  346. action = 0;
  347. else if (!strcasecmp(temp_char, "resume"))
  348. action = 1;
  349. else
  350. for(i = 0; i < NODE_STATE_END; i++) {
  351. upper = node_state_string(i);
  352. if (!strcmp(upper, "UNKNOWN")) {
  353. unknown_found++;
  354. continue;
  355. }
  356. if (!strcasecmp(temp_char, upper)) {
  357. action = i + 2 - unknown_found;
  358. break;
  359. }
  360. }
  361. break;
  362. case SORTID_PREEMPT_MODE:
  363. if (!strcasecmp(temp_char, "cancel"))
  364. action = 0;
  365. else if (!strcasecmp(temp_char, "checkpoint"))
  366. action = 1;
  367. else if (!strcasecmp(temp_char, "off"))
  368. action = 2;
  369. else if (!strcasecmp(temp_char, "requeue"))
  370. action = 3;
  371. else if (!strcasecmp(temp_char, "suspend"))
  372. action = 4;
  373. else
  374. action = 2; /* off */
  375. break;
  376. default:
  377. break;
  378. }
  379. g_free(temp_char);
  380. end_it:
  381. gtk_combo_box_set_active(combo, action);
  382. }
  383. static uint16_t _set_part_share_popup()
  384. {
  385. GtkWidget *table = gtk_table_new(1, 2, FALSE);
  386. GtkWidget *label = NULL;
  387. GtkObject *adjustment = gtk_adjustment_new(4,
  388. 1, 1000,
  389. 1, 60,
  390. 0);
  391. GtkWidget *spin_button =
  392. gtk_spin_button_new(GTK_ADJUSTMENT(adjustment), 1, 0);
  393. GtkWidget *popup = gtk_dialog_new_with_buttons(
  394. "Count",
  395. GTK_WINDOW (main_window),
  396. GTK_DIALOG_MODAL | GTK_DIALOG_DESTROY_WITH_PARENT,
  397. NULL);
  398. int response = 0;
  399. uint16_t count = 4;
  400. label = gtk_dialog_add_button(GTK_DIALOG(popup),
  401. GTK_STOCK_OK, GTK_RESPONSE_OK);
  402. gtk_window_set_default(GTK_WINDOW(popup), label);
  403. label = gtk_label_new("Shared Job Count ");
  404. gtk_container_set_border_width(GTK_CONTAINER(table), 10);
  405. gtk_box_pack_start(GTK_BOX(GTK_DIALOG(popup)->vbox),
  406. table, FALSE, FALSE, 0);
  407. gtk_table_attach_defaults(GTK_TABLE(table), label, 0, 1, 0, 1);
  408. gtk_table_attach_defaults(GTK_TABLE(table), spin_button, 1, 2, 0, 1);
  409. gtk_widget_show_all(popup);
  410. response = gtk_dialog_run (GTK_DIALOG(popup));
  411. if (response == GTK_RESPONSE_OK) {
  412. count = gtk_spin_button_get_value_as_int(
  413. GTK_SPIN_BUTTON(spin_button));
  414. }
  415. gtk_widget_destroy(popup);
  416. return count;
  417. }
  418. /* don't free this char */
  419. static const char *_set_part_msg(update_part_msg_t *part_msg,
  420. const char *new_text,
  421. int column)
  422. {
  423. char *type = "", *temp_char;
  424. int temp_int = 0;
  425. global_edit_error = 0;
  426. if (!part_msg)
  427. return NULL;
  428. switch(column) {
  429. case SORTID_ALTERNATE:
  430. type = "alternate";
  431. part_msg->alternate = xstrdup(new_text);
  432. break;
  433. case SORTID_DEFAULT:
  434. if (!strcasecmp(new_text, "yes")) {
  435. part_msg->flags |= PART_FLAG_DEFAULT;
  436. part_msg->flags &= (~PART_FLAG_DEFAULT_CLR);
  437. } else if (!strcasecmp(new_text, "no")) {
  438. part_msg->flags &= (~PART_FLAG_DEFAULT);
  439. part_msg->flags |= PART_FLAG_DEFAULT_CLR;
  440. }
  441. type = "default";
  442. break;
  443. case SORTID_GRACE_TIME:
  444. temp_int = time_str2mins((char *)new_text);
  445. type = "grace_time";
  446. if (temp_int <= 0)
  447. goto return_error;
  448. /* convert to seconds */
  449. part_msg->grace_time = (uint32_t)(temp_int * 60);
  450. break;
  451. case SORTID_HIDDEN:
  452. if (!strcasecmp(new_text, "yes")) {
  453. part_msg->flags |= PART_FLAG_HIDDEN;
  454. part_msg->flags &= (~PART_FLAG_HIDDEN_CLR);
  455. } else if (!strcasecmp(new_text, "no")) {
  456. part_msg->flags &= (~PART_FLAG_HIDDEN);
  457. part_msg->flags |= PART_FLAG_HIDDEN_CLR;
  458. }
  459. type = "hidden";
  460. break;
  461. case SORTID_TIMELIMIT:
  462. if ((strcasecmp(new_text, "infinite") == 0))
  463. temp_int = INFINITE;
  464. else
  465. temp_int = time_str2mins((char *)new_text);
  466. type = "timelimit";
  467. if ((temp_int <= 0) && (temp_int != INFINITE))
  468. goto return_error;
  469. part_msg->max_time = (uint32_t)temp_int;
  470. break;
  471. case SORTID_PREEMPT_MODE:
  472. if (!strcasecmp(new_text, "cancel"))
  473. part_msg->preempt_mode = PREEMPT_MODE_CANCEL;
  474. else if (!strcasecmp(new_text, "checkpoint"))
  475. part_msg->preempt_mode = PREEMPT_MODE_CHECKPOINT;
  476. else if (!strcasecmp(new_text, "off"))
  477. part_msg->preempt_mode = PREEMPT_MODE_OFF;
  478. else if (!strcasecmp(new_text, "requeue"))
  479. part_msg->preempt_mode = PREEMPT_MODE_REQUEUE;
  480. else if (!strcasecmp(new_text, "suspend"))
  481. part_msg->preempt_mode = PREEMPT_MODE_SUSPEND;
  482. type = "preempt_mode";
  483. break;
  484. case SORTID_PRIORITY:
  485. temp_int = strtol(new_text, (char **)NULL, 10);
  486. type = "priority";
  487. part_msg->priority = (uint16_t)temp_int;
  488. break;
  489. case SORTID_NAME:
  490. type = "name";
  491. part_msg->name = xstrdup(new_text);
  492. break;
  493. case SORTID_NODES_MIN:
  494. temp_int = strtol(new_text, (char **)NULL, 10);
  495. type = "min_nodes";
  496. if (temp_int <= 0)
  497. goto return_error;
  498. part_msg->min_nodes = (uint32_t)temp_int;
  499. break;
  500. case SORTID_NODES_MAX:
  501. if (!strcasecmp(new_text, "infinite")) {
  502. temp_int = INFINITE;
  503. } else {
  504. temp_int = strtol(new_text, &temp_char, 10);
  505. if ((temp_char[0] == 'k') || (temp_char[0] == 'K'))
  506. temp_int *= 1024;
  507. if ((temp_char[0] == 'm') || (temp_char[0] == 'M'))
  508. temp_int *= (1024 * 1024);
  509. }
  510. type = "max_nodes";
  511. if ((temp_int <= 0) && (temp_int != INFINITE))
  512. goto return_error;
  513. part_msg->max_nodes = (uint32_t)temp_int;
  514. break;
  515. case SORTID_ROOT:
  516. if (!strcasecmp(new_text, "yes")) {
  517. part_msg->flags |= PART_FLAG_ROOT_ONLY;
  518. part_msg->flags &= (~PART_FLAG_ROOT_ONLY_CLR);
  519. } else if (!strcasecmp(new_text, "no")) {
  520. part_msg->flags &= (~PART_FLAG_ROOT_ONLY);
  521. part_msg->flags |= PART_FLAG_ROOT_ONLY_CLR;
  522. }
  523. type = "root";
  524. break;
  525. case SORTID_SHARE:
  526. if (!strcasecmp(new_text, "yes")) {
  527. part_msg->max_share = _set_part_share_popup();
  528. } else if (!strcasecmp(new_text, "exclusive")) {
  529. part_msg->max_share = 0;
  530. } else if (!strcasecmp(new_text, "force")) {
  531. part_msg->max_share =
  532. _set_part_share_popup() | SHARED_FORCE;
  533. } else if (!strcasecmp(new_text, "no"))
  534. part_msg->max_share = 1;
  535. else
  536. goto return_error;
  537. type = "share";
  538. break;
  539. case SORTID_GROUPS:
  540. type = "groups";
  541. part_msg->allow_groups = xstrdup(new_text);
  542. break;
  543. case SORTID_NODES_ALLOWED:
  544. type = "allowed alloc nodes";
  545. part_msg->allow_alloc_nodes = xstrdup(new_text);
  546. break;
  547. case SORTID_NODELIST:
  548. part_msg->nodes = xstrdup(new_text);
  549. type = "nodelist";
  550. break;
  551. case SORTID_PART_STATE:
  552. if (!strcasecmp(new_text, "up"))
  553. part_msg->state_up = PARTITION_UP;
  554. else if (!strcasecmp(new_text, "down"))
  555. part_msg->state_up = PARTITION_DOWN;
  556. else if (!strcasecmp(new_text, "inactive"))
  557. part_msg->state_up = PARTITION_INACTIVE;
  558. else if (!strcasecmp(new_text, "drain"))
  559. part_msg->state_up = PARTITION_DRAIN;
  560. else
  561. goto return_error;
  562. type = "availability";
  563. break;
  564. case SORTID_NODE_STATE:
  565. type = (char *)new_text;
  566. got_edit_signal = xstrdup(new_text);
  567. break;
  568. case SORTID_FEATURES:
  569. type = "Update Features";
  570. got_features_edit_signal = xstrdup(new_text);
  571. break;
  572. default:
  573. type = "unknown";
  574. break;
  575. }
  576. if (strcmp(type, "unknown"))
  577. global_send_update_msg = 1;
  578. return type;
  579. return_error:
  580. global_edit_error = 1;
  581. return type;
  582. }
  583. static void _admin_edit_combo_box_part(GtkComboBox *combo,
  584. update_part_msg_t *part_msg)
  585. {
  586. GtkTreeModel *model = NULL;
  587. GtkTreeIter iter;
  588. int column = 0;
  589. char *name = NULL;
  590. if (!part_msg)
  591. return;
  592. if (!gtk_combo_box_get_active_iter(combo, &iter)) {
  593. g_print("nothing selected\n");
  594. return;
  595. }
  596. model = gtk_combo_box_get_model(combo);
  597. if (!model) {
  598. g_print("nothing selected\n");
  599. return;
  600. }
  601. gtk_tree_model_get(model, &iter, 0, &name, -1);
  602. gtk_tree_model_get(model, &iter, 1, &column, -1);
  603. (void) _set_part_msg(part_msg, name, column);
  604. if (name)
  605. g_free(name);
  606. }
  607. static gboolean _admin_focus_out_part(GtkEntry *entry,
  608. GdkEventFocus *event,
  609. update_part_msg_t *part_msg)
  610. {
  611. if (global_entry_changed) {
  612. const char *col_name = NULL;
  613. int type = gtk_entry_get_max_length(entry);
  614. const char *name = gtk_entry_get_text(entry);
  615. type -= DEFAULT_ENTRY_LENGTH;
  616. col_name = _set_part_msg(part_msg, name, type);
  617. if (global_edit_error) {
  618. if (global_edit_error_msg)
  619. g_free(global_edit_error_msg);
  620. global_edit_error_msg = g_strdup_printf(
  621. "Partition %s %s can't be set to %s",
  622. part_msg->name,
  623. col_name,
  624. name);
  625. }
  626. global_entry_changed = 0;
  627. }
  628. return false;
  629. }
  630. static GtkWidget *_admin_full_edit_part(update_part_msg_t *part_msg,
  631. GtkTreeModel *model, GtkTreeIter *iter)
  632. {
  633. GtkScrolledWindow *window = create_scrolled_window();
  634. GtkBin *bin = NULL;
  635. GtkViewport *view = NULL;
  636. GtkTable *table = NULL;
  637. int i = 0, row = 0;
  638. display_data_t *display_data = display_data_part;
  639. gtk_scrolled_window_set_policy(window,
  640. GTK_POLICY_NEVER,
  641. GTK_POLICY_AUTOMATIC);
  642. bin = GTK_BIN(&window->container);
  643. view = GTK_VIEWPORT(bin->child);
  644. bin = GTK_BIN(&view->bin);
  645. table = GTK_TABLE(bin->child);
  646. gtk_table_resize(table, SORTID_CNT, 2);
  647. gtk_table_set_homogeneous(table, FALSE);
  648. for(i = 0; i < SORTID_CNT; i++) {
  649. while (display_data++) {
  650. if (display_data->id == -1)
  651. break;
  652. if (!display_data->name)
  653. continue;
  654. if (display_data->id != i)
  655. continue;
  656. display_admin_edit(
  657. table, part_msg, &row, model, iter,
  658. display_data,
  659. G_CALLBACK(_admin_edit_combo_box_part),
  660. G_CALLBACK(_admin_focus_out_part),
  661. _set_active_combo_part);
  662. break;
  663. }
  664. display_data = display_data_part;
  665. }
  666. gtk_table_resize(table, row, 2);
  667. return GTK_WIDGET(window);
  668. }
  669. static void _subdivide_part(sview_part_info_t *sview_part_info,
  670. GtkTreeModel *model,
  671. GtkTreeIter *sub_iter,
  672. GtkTreeIter *iter)
  673. {
  674. GtkTreeIter first_sub_iter;
  675. ListIterator itr = NULL;
  676. int i = 0, line = 0;
  677. sview_part_sub_t *sview_part_sub = NULL;
  678. int set = 0;
  679. memset(&first_sub_iter, 0, sizeof(GtkTreeIter));
  680. /* make sure all the steps are still here */
  681. if (sub_iter) {
  682. first_sub_iter = *sub_iter;
  683. while (1) {
  684. gtk_tree_store_set(GTK_TREE_STORE(model), sub_iter,
  685. SORTID_UPDATED, 0, -1);
  686. if (!gtk_tree_model_iter_next(model, sub_iter)) {
  687. break;
  688. }
  689. }
  690. memcpy(sub_iter, &first_sub_iter, sizeof(GtkTreeIter));
  691. set = 1;
  692. }
  693. itr = list_iterator_create(sview_part_info->sub_list);
  694. if (list_count(sview_part_info->sub_list) == 1) {
  695. gtk_tree_store_set(GTK_TREE_STORE(model), iter,
  696. SORTID_ONLY_LINE, 1, -1);
  697. sview_part_sub = list_next(itr);
  698. _update_part_sub_record(sview_part_sub,
  699. GTK_TREE_STORE(model),
  700. iter);
  701. } else {
  702. while ((sview_part_sub = list_next(itr))) {
  703. if (!sub_iter) {
  704. i = NO_VAL;
  705. goto adding;
  706. } else {
  707. memcpy(sub_iter, &first_sub_iter,
  708. sizeof(GtkTreeIter));
  709. }
  710. line = 0;
  711. while (1) {
  712. int state;
  713. /* Search for the state number and
  714. check to see if it is in the
  715. list. Here we need to pass an int
  716. for system where endian is an
  717. issue passing a uint16_t may seg
  718. fault. */
  719. gtk_tree_model_get(model, sub_iter,
  720. SORTID_NODE_STATE_NUM,
  721. &state, -1);
  722. if ((uint16_t)state
  723. == sview_part_sub->node_state) {
  724. /* update with new info */
  725. _update_part_sub_record(
  726. sview_part_sub,
  727. GTK_TREE_STORE(model),
  728. sub_iter);
  729. goto found;
  730. }
  731. line++;
  732. if (!gtk_tree_model_iter_next(model,
  733. sub_iter)) {
  734. break;
  735. }
  736. }
  737. adding:
  738. _append_part_sub_record(sview_part_sub,
  739. GTK_TREE_STORE(model),
  740. iter, line);
  741. /* if (i == NO_VAL) */
  742. /* line++; */
  743. found:
  744. ;
  745. }
  746. }
  747. list_iterator_destroy(itr);
  748. if (set) {
  749. sub_iter = &first_sub_iter;
  750. /* clear all steps that aren't active */
  751. while (1) {
  752. gtk_tree_model_get(model, sub_iter,
  753. SORTID_UPDATED, &i, -1);
  754. if (!i) {
  755. if (!gtk_tree_store_remove(
  756. GTK_TREE_STORE(model),
  757. sub_iter))
  758. break;
  759. else
  760. continue;
  761. }
  762. if (!gtk_tree_model_iter_next(model, sub_iter)) {
  763. break;
  764. }
  765. }
  766. }
  767. return;
  768. }
  769. static void _layout_part_record(GtkTreeView *treeview,
  770. sview_part_info_t *sview_part_info,
  771. int update)
  772. {
  773. GtkTreeIter iter;
  774. char time_buf[20], tmp_buf[20];
  775. char tmp_cnt[8];
  776. char tmp_cnt1[8];
  777. char tmp_cnt2[8];
  778. partition_info_t *part_ptr = sview_part_info->part_ptr;
  779. sview_part_sub_t *sview_part_sub = NULL;
  780. char ind_cnt[1024];
  781. char *temp_char = NULL;
  782. uint16_t temp_uint16 = 0;
  783. int i;
  784. int yes_no = -1;
  785. int up_down = -1;
  786. uint32_t limit_set = NO_VAL;
  787. GtkTreeStore *treestore =
  788. GTK_TREE_STORE(gtk_tree_view_get_model(treeview));
  789. convert_num_unit((float)sview_part_info->sub_part_total.cpu_alloc_cnt
  790. / cpus_per_node,
  791. tmp_cnt, sizeof(tmp_cnt), UNIT_NONE);
  792. convert_num_unit((float)sview_part_info->sub_part_total.cpu_idle_cnt
  793. / cpus_per_node,
  794. tmp_cnt1, sizeof(tmp_cnt1), UNIT_NONE);
  795. convert_num_unit((float)sview_part_info->sub_part_total.cpu_error_cnt
  796. / cpus_per_node,
  797. tmp_cnt2, sizeof(tmp_cnt2), UNIT_NONE);
  798. snprintf(ind_cnt, sizeof(ind_cnt), "%s/%s/%s",
  799. tmp_cnt, tmp_cnt1, tmp_cnt2);
  800. for (i = 0; i < SORTID_CNT; i++) {
  801. switch (i) {
  802. case SORTID_PART_STATE:
  803. switch(part_ptr->state_up) {
  804. case PARTITION_UP:
  805. temp_char = "up";
  806. break;
  807. case PARTITION_DOWN:
  808. temp_char = "down";
  809. break;
  810. case PARTITION_INACTIVE:
  811. temp_char = "inactive";
  812. break;
  813. case PARTITION_DRAIN:
  814. temp_char = "drain";
  815. break;
  816. default:
  817. temp_char = "unknown";
  818. break;
  819. }
  820. break;
  821. case SORTID_ALTERNATE:
  822. if (part_ptr->alternate)
  823. temp_char = part_ptr->alternate;
  824. else
  825. temp_char = "";
  826. break;
  827. case SORTID_CPUS:
  828. convert_num_unit((float)part_ptr->total_cpus,
  829. tmp_cnt, sizeof(tmp_cnt),
  830. UNIT_NONE);
  831. temp_char = tmp_cnt;
  832. break;
  833. case SORTID_DEFAULT:
  834. if (part_ptr->flags & PART_FLAG_DEFAULT)
  835. yes_no = 1;
  836. else
  837. yes_no = 0;
  838. break;
  839. case SORTID_FEATURES:
  840. if (sview_part_sub)
  841. temp_char = sview_part_sub->features;
  842. else
  843. temp_char = "";
  844. break;
  845. case SORTID_GRACE_TIME:
  846. limit_set = part_ptr->grace_time;
  847. break;
  848. case SORTID_GROUPS:
  849. if (part_ptr->allow_groups)
  850. temp_char = part_ptr->allow_groups;
  851. else
  852. temp_char = "all";
  853. break;
  854. case SORTID_HIDDEN:
  855. if (part_ptr->flags & PART_FLAG_HIDDEN)
  856. yes_no = 1;
  857. else
  858. yes_no = 0;
  859. break;
  860. case SORTID_JOB_SIZE:
  861. _build_min_max_32_string(time_buf, sizeof(time_buf),
  862. part_ptr->min_nodes,
  863. part_ptr->max_nodes, true);
  864. temp_char = time_buf;
  865. break;
  866. case SORTID_MEM:
  867. convert_num_unit((float)sview_part_info->
  868. sub_part_total.mem_total,
  869. tmp_cnt, sizeof(tmp_cnt),
  870. UNIT_MEGA);
  871. temp_char = tmp_cnt;
  872. break;
  873. case SORTID_NODELIST:
  874. temp_char = part_ptr->nodes;
  875. break;
  876. case SORTID_NODES_ALLOWED:
  877. temp_char = part_ptr->allow_alloc_nodes;
  878. break;
  879. case SORTID_NODES:
  880. if (cluster_flags & CLUSTER_FLAG_BG)
  881. convert_num_unit((float)part_ptr->total_nodes,
  882. tmp_cnt,
  883. sizeof(tmp_cnt), UNIT_NONE);
  884. else
  885. sprintf(tmp_cnt, "%u", part_ptr->total_nodes);
  886. temp_char = tmp_cnt;
  887. break;
  888. case SORTID_NODES_MAX:
  889. limit_set = part_ptr->max_nodes;
  890. break;
  891. case SORTID_NODES_MIN:
  892. limit_set = part_ptr->min_nodes;
  893. break;
  894. case SORTID_NODE_INX:
  895. break;
  896. case SORTID_ONLY_LINE:
  897. break;
  898. case SORTID_PREEMPT_MODE:
  899. temp_uint16 = part_ptr->preempt_mode;
  900. if (temp_uint16 == (uint16_t) NO_VAL)
  901. temp_uint16 = slurm_get_preempt_mode();
  902. temp_char = preempt_mode_string(temp_uint16);
  903. break;
  904. case SORTID_PRIORITY:
  905. convert_num_unit((float)part_ptr->priority,
  906. time_buf, sizeof(time_buf), UNIT_NONE);
  907. temp_char = time_buf;
  908. break;
  909. case SORTID_REASON:
  910. sview_part_sub = list_peek(sview_part_info->sub_list);
  911. if (sview_part_sub)
  912. temp_char = sview_part_sub->reason;
  913. else
  914. temp_char = "";
  915. break;
  916. case SORTID_ROOT:
  917. if (part_ptr->flags & PART_FLAG_ROOT_ONLY)
  918. yes_no = 1;
  919. else
  920. yes_no = 0;
  921. break;
  922. case SORTID_SHARE:
  923. if (part_ptr->max_share & SHARED_FORCE) {
  924. snprintf(tmp_buf, sizeof(tmp_buf), "force:%u",
  925. (part_ptr->max_share
  926. & ~(SHARED_FORCE)));
  927. temp_char = tmp_buf;
  928. } else if (part_ptr->max_share == 0)
  929. temp_char = "exclusive";
  930. else if (part_ptr->max_share > 1) {
  931. snprintf(tmp_buf, sizeof(tmp_buf), "yes:%u",
  932. part_ptr->max_share);
  933. temp_char = tmp_buf;
  934. } else
  935. temp_char = "no";
  936. break;
  937. case SORTID_TMP_DISK:
  938. convert_num_unit(
  939. (float)sview_part_info->sub_part_total.
  940. disk_total,
  941. time_buf, sizeof(time_buf), UNIT_NONE);
  942. temp_char = time_buf;
  943. break;
  944. case SORTID_TIMELIMIT:
  945. limit_set = part_ptr->max_time;
  946. break;
  947. default:
  948. break;
  949. }
  950. if (up_down != -1) {
  951. if (up_down)
  952. temp_char = "up";
  953. else
  954. temp_char = "down";
  955. up_down = -1;
  956. } if (yes_no != -1) {
  957. if (yes_no)
  958. temp_char = "yes";
  959. else
  960. temp_char = "no";
  961. yes_no = -1;
  962. } else if (limit_set != NO_VAL) {
  963. if (limit_set == (uint32_t) INFINITE)
  964. temp_char = "infinite";
  965. else {
  966. convert_num_unit(
  967. (float)limit_set,
  968. time_buf, sizeof(time_buf), UNIT_NONE);
  969. temp_char = time_buf;
  970. }
  971. limit_set = NO_VAL;
  972. }
  973. if (temp_char) {
  974. add_display_treestore_line(
  975. update, treestore, &iter,
  976. find_col_name(display_data_part,
  977. i),
  978. temp_char);
  979. if (i == SORTID_NODES) {
  980. add_display_treestore_line(
  981. update, treestore, &iter,
  982. "Nodes (Allocated/Idle/Other)",
  983. ind_cnt);
  984. }
  985. temp_char = NULL;
  986. }
  987. }
  988. }
  989. static void _update_part_record(sview_part_info_t *sview_part_info,
  990. GtkTreeStore *treestore)
  991. {
  992. char tmp_prio[40], tmp_size[40], tmp_share_buf[40], tmp_time[40];
  993. char tmp_max_nodes[40], tmp_min_nodes[40], tmp_grace[40];
  994. char tmp_cpu_cnt[40], tmp_node_cnt[40];
  995. char *tmp_alt, *tmp_default, *tmp_groups, *tmp_hidden;
  996. char *tmp_root, *tmp_share, *tmp_state;
  997. uint16_t tmp_preempt;
  998. partition_info_t *part_ptr = sview_part_info->part_ptr;
  999. GtkTreeIter sub_iter;
  1000. if (part_ptr->alternate)
  1001. tmp_alt = part_ptr->alternate;
  1002. else
  1003. tmp_alt = "";
  1004. if (cluster_flags & CLUSTER_FLAG_BG)
  1005. convert_num_unit((float)part_ptr->total_cpus, tmp_cpu_cnt,
  1006. sizeof(tmp_cpu_cnt), UNIT_NONE);
  1007. else
  1008. sprintf(tmp_cpu_cnt, "%u", part_ptr->total_cpus);
  1009. if (part_ptr->flags & PART_FLAG_DEFAULT)
  1010. tmp_default = "yes";
  1011. else
  1012. tmp_default = "no";
  1013. if (part_ptr->allow_groups)
  1014. tmp_groups = part_ptr->allow_groups;
  1015. else
  1016. tmp_groups = "all";
  1017. if (part_ptr->flags & PART_FLAG_HIDDEN)
  1018. tmp_hidden = "yes";
  1019. else
  1020. tmp_hidden = "no";
  1021. if (part_ptr->grace_time == (uint32_t) NO_VAL)
  1022. snprintf(tmp_grace, sizeof(tmp_grace), "none");
  1023. else {
  1024. secs2time_str(part_ptr->grace_time,
  1025. tmp_grace, sizeof(tmp_grace));
  1026. }
  1027. if (part_ptr->max_nodes == (uint32_t) INFINITE)
  1028. snprintf(tmp_max_nodes, sizeof(tmp_max_nodes), "infinite");
  1029. else {
  1030. convert_num_unit((float)part_ptr->max_nodes,
  1031. tmp_max_nodes, sizeof(tmp_max_nodes),
  1032. UNIT_NONE);
  1033. }
  1034. if (part_ptr->min_nodes == (uint32_t) INFINITE)
  1035. snprintf(tmp_min_nodes, sizeof(tmp_min_nodes), "infinite");
  1036. else {
  1037. convert_num_unit((float)part_ptr->min_nodes,
  1038. tmp_min_nodes, sizeof(tmp_min_nodes), UNIT_NONE);
  1039. }
  1040. if (cluster_flags & CLUSTER_FLAG_BG)
  1041. convert_num_unit((float)part_ptr->total_nodes, tmp_node_cnt,
  1042. sizeof(tmp_node_cnt), UNIT_NONE);
  1043. else
  1044. sprintf(tmp_node_cnt, "%u", part_ptr->total_nodes);
  1045. if (part_ptr->flags & PART_FLAG_ROOT_ONLY)
  1046. tmp_root = "yes";
  1047. else
  1048. tmp_root = "no";
  1049. if (part_ptr->state_up == PARTITION_UP)
  1050. tmp_state = "up";
  1051. else if (part_ptr->state_up == PARTITION_DOWN)
  1052. tmp_state = "down";
  1053. else if (part_ptr->state_up == PARTITION_INACTIVE)
  1054. tmp_state = "inact";
  1055. else if (part_ptr->state_up == PARTITION_DRAIN)
  1056. tmp_state = "drain";
  1057. else
  1058. tmp_state = "unk";
  1059. _build_min_max_32_string(tmp_size, sizeof(tmp_size),
  1060. part_ptr->min_nodes,
  1061. part_ptr->max_nodes, true);
  1062. tmp_preempt = part_ptr->preempt_mode;
  1063. if (tmp_preempt == (uint16_t) NO_VAL)
  1064. tmp_preempt = slurm_get_preempt_mode(); /* use cluster param */
  1065. convert_num_unit((float)part_ptr->priority,
  1066. tmp_prio, sizeof(tmp_prio), UNIT_NONE);
  1067. if (part_ptr->max_share & SHARED_FORCE) {
  1068. snprintf(tmp_share_buf, sizeof(tmp_share_buf), "force:%u",
  1069. (part_ptr->max_share & ~(SHARED_FORCE)));
  1070. tmp_share = tmp_share_buf;
  1071. } else if (part_ptr->max_share == 0) {
  1072. tmp_share = "exclusive";
  1073. } else if (part_ptr->max_share > 1) {
  1074. snprintf(tmp_share_buf, sizeof(tmp_share_buf), "yes:%u",
  1075. part_ptr->max_share);
  1076. tmp_share = tmp_share_buf;
  1077. } else
  1078. tmp_share = "no";
  1079. if (part_ptr->max_time == INFINITE)
  1080. snprintf(tmp_time, sizeof(tmp_time), "infinite");
  1081. else {
  1082. secs2time_str((part_ptr->max_time * 60),
  1083. tmp_time, sizeof(tmp_time));
  1084. }
  1085. /* Combining these records provides a slight performance improvement
  1086. * NOTE: Some of these fields are cleared here and filled in based upon
  1087. * the configuration of nodes within this partition. */
  1088. gtk_tree_store_set(treestore, &sview_part_info->iter_ptr,
  1089. SORTID_ALTERNATE, tmp_alt,
  1090. SORTID_COLOR,
  1091. sview_colors[sview_part_info->color_inx],
  1092. SORTID_COLOR_INX, sview_part_info->color_inx,
  1093. SORTID_CPUS, tmp_cpu_cnt,
  1094. SORTID_DEFAULT, tmp_default,
  1095. SORTID_FEATURES, "",
  1096. SORTID_GRACE_TIME, tmp_grace,
  1097. SORTID_GROUPS, tmp_groups,
  1098. SORTID_HIDDEN, tmp_hidden,
  1099. SORTID_JOB_SIZE, tmp_size,
  1100. SORTID_MEM, "",
  1101. SORTID_NAME, part_ptr->name,
  1102. SORTID_NODE_INX, part_ptr->node_inx,
  1103. SORTID_NODE_STATE, "",
  1104. SORTID_NODE_STATE_NUM, -1,
  1105. SORTID_NODES, tmp_node_cnt,
  1106. SORTID_NODES_MAX, tmp_max_nodes,
  1107. SORTID_NODES_MIN, tmp_min_nodes,
  1108. SORTID_NODELIST, part_ptr->nodes,
  1109. SORTID_ONLY_LINE, 0,
  1110. SORTID_PART_STATE, tmp_state,
  1111. SORTID_PREEMPT_MODE,
  1112. preempt_mode_string(tmp_preempt),
  1113. SORTID_PRIORITY, tmp_prio,
  1114. SORTID_REASON, "",
  1115. SORTID_ROOT, tmp_root,
  1116. SORTID_SHARE, tmp_share,
  1117. SORTID_TIMELIMIT, tmp_time,
  1118. SORTID_TMP_DISK, "",
  1119. SORTID_UPDATED, 1,
  1120. -1);
  1121. if (gtk_tree_model_iter_children(GTK_TREE_MODEL(treestore),
  1122. &sub_iter,
  1123. &sview_part_info->iter_ptr))
  1124. _subdivide_part(sview_part_info,
  1125. GTK_TREE_MODEL(treestore), &sub_iter,
  1126. &sview_part_info->iter_ptr);
  1127. else
  1128. _subdivide_part(sview_part_info,
  1129. GTK_TREE_MODEL(treestore), NULL,
  1130. &sview_part_info->iter_ptr);
  1131. return;
  1132. }
  1133. static void _update_part_sub_record(sview_part_sub_t *sview_part_sub,
  1134. GtkTreeStore *treestore, GtkTreeIter *iter)
  1135. {
  1136. partition_info_t *part_ptr = sview_part_sub->part_ptr;
  1137. char *tmp_cpus = NULL, *tmp_nodes = NULL, *tmp_nodelist;
  1138. char *tmp_state_lower, *tmp_state_upper;
  1139. char tmp_cnt[40], tmp_disk[40], tmp_mem[40];
  1140. tmp_state_upper = node_state_string(sview_part_sub->node_state);
  1141. tmp_state_lower = str_tolower(tmp_state_upper);
  1142. if ((sview_part_sub->node_state & NODE_STATE_BASE)
  1143. == NODE_STATE_MIXED) {
  1144. if (sview_part_sub->cpu_alloc_cnt) {
  1145. convert_num_unit((float)sview_part_sub->cpu_alloc_cnt,
  1146. tmp_cnt,
  1147. sizeof(tmp_cnt), UNIT_NONE);
  1148. xstrfmtcat(tmp_cpus, "Alloc:%s", tmp_cnt);
  1149. if (cluster_flags & CLUSTER_FLAG_BG) {
  1150. convert_num_unit(
  1151. (float)(sview_part_sub->cpu_alloc_cnt
  1152. / cpus_per_node),
  1153. tmp_cnt,
  1154. sizeof(tmp_cnt), UNIT_NONE);
  1155. xstrfmtcat(tmp_nodes, "Alloc:%s", tmp_cnt);
  1156. }
  1157. }
  1158. if (sview_part_sub->cpu_error_cnt) {
  1159. convert_num_unit((float)sview_part_sub->cpu_error_cnt,
  1160. tmp_cnt,
  1161. sizeof(tmp_cnt), UNIT_NONE);
  1162. if (tmp_cpus)
  1163. xstrcat(tmp_cpus, " ");
  1164. xstrfmtcat(tmp_cpus, "Err:%s", tmp_cnt);
  1165. if (cluster_flags & CLUSTER_FLAG_BG) {
  1166. convert_num_unit(
  1167. (float)(sview_part_sub->cpu_error_cnt
  1168. / cpus_per_node),
  1169. tmp_cnt,
  1170. sizeof(tmp_cnt), UNIT_NONE);
  1171. if (tmp_nodes)
  1172. xstrcat(tmp_nodes, " ");
  1173. xstrfmtcat(tmp_nodes, "Err:%s", tmp_cnt);
  1174. }
  1175. }
  1176. if (sview_part_sub->cpu_idle_cnt) {
  1177. convert_num_unit((float)sview_part_sub->cpu_idle_cnt,
  1178. tmp_cnt,
  1179. sizeof(tmp_cnt), UNIT_NONE);
  1180. if (tmp_cpus)
  1181. xstrcat(tmp_cpus, " ");
  1182. xstrfmtcat(tmp_cpus, "Idle:%s", tmp_cnt);
  1183. if (cluster_flags & CLUSTER_FLAG_BG) {
  1184. convert_num_unit(
  1185. (float)(sview_part_sub->cpu_idle_cnt
  1186. / cpus_per_node),
  1187. tmp_cnt,
  1188. sizeof(tmp_cnt), UNIT_NONE);
  1189. if (tmp_nodes)
  1190. xstrcat(tmp_nodes, " ");
  1191. xstrfmtcat(tmp_nodes, "Idle:%s", tmp_cnt);
  1192. }
  1193. }
  1194. } else {
  1195. tmp_cpus = xmalloc(20);
  1196. convert_num_unit((float)sview_part_sub->cpu_idle_cnt,
  1197. tmp_cpus, 20, UNIT_NONE);
  1198. }
  1199. if (!tmp_nodes) {
  1200. convert_num_unit((float)sview_part_sub->node_cnt, tmp_cnt,
  1201. sizeof(tmp_cnt), UNIT_NONE);
  1202. tmp_nodes = xstrdup(tmp_cnt);
  1203. }
  1204. convert_num_unit((float)sview_part_sub->disk_total, tmp_disk,
  1205. sizeof(tmp_disk), UNIT_NONE);
  1206. convert_num_unit((float)sview_part_sub->mem_total, tmp_mem,
  1207. sizeof(tmp_mem), UNIT_MEGA);
  1208. tmp_nodelist = hostlist_ranged_string_xmalloc(sview_part_sub->hl);
  1209. gtk_tree_store_set(treestore, iter,
  1210. SORTID_CPUS, tmp_cpus,
  1211. SORTID_FEATURES, sview_part_sub->features,
  1212. SORTID_MEM, tmp_mem,
  1213. SORTID_NAME, part_ptr->name,
  1214. SORTID_NODE_STATE_NUM, sview_part_sub->node_state,
  1215. SORTID_NODELIST, tmp_nodelist,
  1216. SORTID_NODES, tmp_nodes,
  1217. SORTID_NODE_STATE, tmp_state_lower,
  1218. SORTID_REASON, sview_part_sub->reason,
  1219. SORTID_TMP_DISK, tmp_disk,
  1220. SORTID_UPDATED, 1,
  1221. -1);
  1222. xfree(tmp_cpus);
  1223. xfree(tmp_nodelist);
  1224. xfree(tmp_nodes);
  1225. xfree(tmp_state_lower);
  1226. return;
  1227. }
  1228. static void _append_part_record(sview_part_info_t *sview_part_info,
  1229. GtkTreeStore *treestore)
  1230. {
  1231. gtk_tree_store_append(treestore, &sview_part_info->iter_ptr, NULL);
  1232. gtk_tree_store_set(treestore, &sview_part_info->iter_ptr,
  1233. SORTID_POS, sview_part_info->pos, -1);
  1234. _update_part_record(sview_part_info, treestore);
  1235. }
  1236. static void _append_part_sub_record(sview_part_sub_t *sview_part_sub,
  1237. GtkTreeStore *treestore, GtkTreeIter *iter,
  1238. int line)
  1239. {
  1240. GtkTreeIter sub_iter;
  1241. gtk_tree_store_append(treestore, &sub_iter, iter);
  1242. gtk_tree_store_set(treestore, &sub_iter, SORTID_POS, line, -1);
  1243. _update_part_sub_record(sview_part_sub, treestore, &sub_iter);
  1244. }
  1245. static void _update_info_part(List info_list,
  1246. GtkTreeView *tree_view)
  1247. {
  1248. GtkTreeModel *model = gtk_tree_view_get_model(tree_view);
  1249. static GtkTreeModel *last_model = NULL;
  1250. partition_info_t *part_ptr = NULL;
  1251. char *name = NULL;
  1252. ListIterator itr = NULL;
  1253. sview_part_info_t *sview_part_info = NULL;
  1254. set_for_update(model, SORTID_UPDATED);
  1255. itr = list_iterator_create(info_list);
  1256. while ((sview_part_info = (sview_part_info_t*) list_next(itr))) {
  1257. part_ptr = sview_part_info->part_ptr;
  1258. /* This means the tree_store changed (added new column
  1259. or something). */
  1260. if (last_model != model)
  1261. sview_part_info->iter_set = false;
  1262. if (sview_part_info->iter_set) {
  1263. gtk_tree_model_get(model, &sview_part_info->iter_ptr,
  1264. SORTID_NAME, &name, -1);
  1265. if (strcmp(name, part_ptr->name)) /* Bad pointer */
  1266. sview_part_info->iter_set = false;
  1267. g_free(name);
  1268. }
  1269. if (sview_part_info->iter_set)
  1270. _update_part_record(sview_part_info,
  1271. GTK_TREE_STORE(model));
  1272. else {
  1273. GtkTreePath *path = gtk_tree_path_new_first();
  1274. /* get the iter, or find out the list is empty
  1275. * goto add */
  1276. if (gtk_tree_model_get_iter(
  1277. model, &sview_part_info->iter_ptr, path)) {
  1278. do {
  1279. /* search for the jobid and
  1280. check to see if it is in
  1281. the list */
  1282. gtk_tree_model_get(
  1283. model,
  1284. &sview_part_info->iter_ptr,
  1285. SORTID_NAME,
  1286. &name, -1);
  1287. if (!strcmp(name, part_ptr->name)) {
  1288. /* update with new info */
  1289. g_free(name);
  1290. _update_part_record(
  1291. sview_part_info,
  1292. GTK_TREE_STORE(model));
  1293. sview_part_info->iter_set = 1;
  1294. break;
  1295. }
  1296. g_free(name);
  1297. } while (gtk_tree_model_iter_next(
  1298. model,
  1299. &sview_part_info->iter_ptr));
  1300. }
  1301. if (!sview_part_info->iter_set) {
  1302. _append_part_record(sview_part_info,
  1303. GTK_TREE_STORE(model));
  1304. sview_part_info->iter_set = true;
  1305. }
  1306. gtk_tree_path_free(path);
  1307. }
  1308. }
  1309. list_iterator_destroy(itr);
  1310. /* remove all old partitions */
  1311. remove_old(model, SORTID_UPDATED);
  1312. last_model = model;
  1313. return;
  1314. }
  1315. static void _part_info_list_del(void *object)
  1316. {
  1317. sview_part_info_t *sview_part_info = (sview_part_info_t *)object;
  1318. if (sview_part_info) {
  1319. if (sview_part_info->sub_list)
  1320. list_destroy(sview_part_info->sub_list);
  1321. xfree(sview_part_info);
  1322. }
  1323. }
  1324. static void _destroy_part_sub(void *object)
  1325. {
  1326. sview_part_sub_t *sview_part_sub = (sview_part_sub_t *)object;
  1327. if (sview_part_sub) {
  1328. xfree(sview_part_sub->features);
  1329. xfree(sview_part_sub->reason);
  1330. if (sview_part_sub->hl)
  1331. hostlist_destroy(sview_part_sub->hl);
  1332. if (sview_part_sub->node_ptr_list)
  1333. list_destroy(sview_part_sub->node_ptr_list);
  1334. xfree(sview_part_sub);
  1335. }
  1336. }
  1337. static void _update_sview_part_sub(sview_part_sub_t *sview_part_sub,
  1338. node_info_t *node_ptr,
  1339. int node_scaling)
  1340. {
  1341. int cpus_per_node = 1;
  1342. int idle_cpus = node_ptr->cpus;
  1343. uint16_t err_cpus = 0, alloc_cpus = 0;
  1344. if (node_scaling)
  1345. cpus_per_node = node_ptr->cpus / node_scaling;
  1346. xassert(sview_part_sub);
  1347. xassert(sview_part_sub->node_ptr_list);
  1348. xassert(sview_part_sub->hl);
  1349. if (sview_part_sub->node_cnt == 0) { /* first node added */
  1350. sview_part_sub->node_state = node_ptr->node_state;
  1351. sview_part_sub->features = xstrdup(node_ptr->features);
  1352. sview_part_sub->reason = xstrdup(node_ptr->reason);
  1353. } else if (hostlist_find(sview_part_sub->hl, node_ptr->name) != -1) {
  1354. /* we already have this node in this record,
  1355. * just return, don't duplicate */
  1356. g_print("already been here\n");
  1357. return;
  1358. }
  1359. if ((sview_part_sub->node_state & NODE_STATE_BASE)
  1360. == NODE_STATE_MIXED) {
  1361. slurm_get_select_nodeinfo(node_ptr->select_nodeinfo,
  1362. SELECT_NODEDATA_SUBCNT,
  1363. NODE_STATE_ALLOCATED,
  1364. &alloc_cpus);
  1365. if (cluster_flags & CLUSTER_FLAG_BG) {
  1366. if (!alloc_cpus
  1367. && (IS_NODE_ALLOCATED(node_ptr)
  1368. || IS_NODE_COMPLETING(node_ptr)))
  1369. alloc_cpus = node_ptr->cpus;
  1370. else
  1371. alloc_cpus *= cpus_per_node;
  1372. }
  1373. idle_cpus -= alloc_cpus;
  1374. slurm_get_select_nodeinfo(node_ptr->select_nodeinfo,
  1375. SELECT_NODEDATA_SUBCNT,
  1376. NODE_STATE_ERROR,
  1377. &err_cpus);
  1378. if (cluster_flags & CLUSTER_FLAG_BG)
  1379. err_cpus *= cpus_per_node;
  1380. idle_cpus -= err_cpus;
  1381. } else if (sview_part_sub->node_state == NODE_STATE_ALLOCATED) {
  1382. alloc_cpus = idle_cpus;
  1383. idle_cpus = 0;
  1384. } else if (sview_part_sub->node_state != NODE_STATE_IDLE) {
  1385. err_cpus = idle_cpus;
  1386. idle_cpus = 0;
  1387. }
  1388. sview_part_sub->cpu_alloc_cnt += alloc_cpus;
  1389. sview_part_sub->cpu_error_cnt += err_cpus;
  1390. sview_part_sub->cpu_idle_cnt += idle_cpus;
  1391. sview_part_sub->disk_total += node_ptr->tmp_disk;
  1392. sview_part_sub->mem_total += node_ptr->real_memory;
  1393. sview_part_sub->node_cnt += node_scaling;
  1394. list_append(sview_part_sub->node_ptr_list, node_ptr);
  1395. hostlist_push(sview_part_sub->hl, node_ptr->name);
  1396. }
  1397. /*
  1398. * _create_sview_part_sub - create an sview_part_sub record for
  1399. * the given partition
  1400. * sview_part_sub OUT - ptr to an inited sview_part_sub_t
  1401. */
  1402. static sview_part_sub_t *_create_sview_part_sub(partition_info_t *part_ptr,
  1403. node_info_t *node_ptr,
  1404. int node_scaling)
  1405. {
  1406. sview_part_sub_t *sview_part_sub_ptr =
  1407. xmalloc(sizeof(sview_part_sub_t));
  1408. if (!part_ptr) {
  1409. g_print("got no part_ptr!\n");
  1410. xfree(sview_part_sub_ptr);
  1411. return NULL;
  1412. }
  1413. if (!node_ptr) {
  1414. g_print("got no node_ptr!\n");
  1415. xfree(sview_part_sub_ptr);
  1416. return NULL;
  1417. }
  1418. sview_part_sub_ptr->part_ptr = part_ptr;
  1419. sview_part_sub_ptr->hl = hostlist_create("");
  1420. sview_part_sub_ptr->node_ptr_list = list_create(NULL);
  1421. _update_sview_part_sub(sview_part_sub_ptr, node_ptr, node_scaling);
  1422. return sview_part_sub_ptr;
  1423. }
  1424. static int _insert_sview_part_sub(sview_part_info_t *sview_part_info,
  1425. partition_info_t *part_ptr,
  1426. node_info_t *node_ptr,
  1427. int node_scaling)
  1428. {
  1429. sview_part_sub_t *sview_part_sub = NULL;
  1430. ListIterator itr = list_iterator_create(sview_part_info->sub_list);
  1431. while ((sview_part_sub = list_next(itr))) {
  1432. if (sview_part_sub->node_state
  1433. == node_ptr->node_state) {
  1434. _update_sview_part_sub(sview_part_sub,
  1435. node_ptr,
  1436. node_scaling);
  1437. break;
  1438. }
  1439. }
  1440. list_iterator_destroy(itr);
  1441. if (!sview_part_sub) {
  1442. if ((sview_part_sub = _create_sview_part_sub(
  1443. part_ptr, node_ptr, node_scaling)))
  1444. list_push(sview_part_info->sub_list,
  1445. sview_part_sub);
  1446. }
  1447. return SLURM_SUCCESS;
  1448. }
  1449. /*
  1450. * _create_sview_part_info - create an sview_part_info record for
  1451. * the given partition
  1452. * part_ptr IN - pointer to partition record to add
  1453. * sview_part_info OUT - ptr to an inited sview_part_info_t
  1454. */
  1455. static sview_part_info_t *_create_sview_part_info(partition_info_t* part_ptr)
  1456. {
  1457. sview_part_info_t *sview_part_info =
  1458. xmalloc(sizeof(sview_part_info_t));
  1459. sview_part_info->part_ptr = part_ptr;
  1460. sview_part_info->sub_list = list_create(_destroy_part_sub);
  1461. return sview_part_info;
  1462. }
  1463. static int _sview_part_sort_aval_dec(sview_part_info_t* rec_a,
  1464. sview_part_info_t* rec_b)
  1465. {
  1466. int size_a = rec_a->part_ptr->total_nodes;
  1467. int size_b = rec_b->part_ptr->total_nodes;
  1468. if (size_a < size_b)
  1469. return -1;
  1470. else if (size_a > size_b)
  1471. return 1;
  1472. if (rec_a->part_ptr->nodes && rec_b->part_ptr->nodes) {
  1473. size_a = strcmp(rec_a->part_ptr->nodes, rec_b->part_ptr->nodes);
  1474. if (size_a < 0)
  1475. return -1;
  1476. else if (size_a > 0)
  1477. return 1;
  1478. }
  1479. return 0;
  1480. }
  1481. static int _sview_sub_part_sort(sview_part_sub_t* rec_a,
  1482. sview_part_sub_t* rec_b)
  1483. {
  1484. int size_a = rec_a->node_state & NODE_STATE_BASE;
  1485. int size_b = rec_b->node_state & NODE_STATE_BASE;
  1486. if (size_a < size_b)
  1487. return -1;
  1488. else if (size_a > size_b)
  1489. return 1;
  1490. return 0;
  1491. }
  1492. static List _create_part_info_list(partition_info_msg_t *part_info_ptr,
  1493. node_info_msg_t *node_info_ptr)
  1494. {
  1495. sview_part_info_t *sview_part_info = NULL;
  1496. partition_info_t *part_ptr = NULL;
  1497. static node_info_msg_t *last_node_info_ptr = NULL;
  1498. static partition_info_msg_t *last_part_info_ptr = NULL;
  1499. node_info_t *node_ptr = NULL;
  1500. static List info_list = NULL;
  1501. int i, j2;
  1502. sview_part_sub_t *sview_part_sub = NULL;
  1503. ListIterator itr;
  1504. if (info_list && (node_info_ptr == last_node_info_ptr)
  1505. && (part_info_ptr == last_part_info_ptr))
  1506. return info_list;
  1507. last_node_info_ptr = node_info_ptr;
  1508. last_part_info_ptr = part_info_ptr;
  1509. if (info_list)
  1510. list_flush(info_list);
  1511. else
  1512. info_list = list_create(_part_info_list_del);
  1513. if (!info_list) {
  1514. g_print("malloc error\n");
  1515. return NULL;
  1516. }
  1517. for (i=0; i<part_info_ptr->record_count; i++) {
  1518. part_ptr = &(part_info_ptr->partition_array[i]);
  1519. /* don't include configured excludes */
  1520. if (!working_sview_config.show_hidden &&
  1521. part_ptr->flags & PART_FLAG_HIDDEN)
  1522. continue;
  1523. sview_part_info = _create_sview_part_info(part_ptr);
  1524. sview_part_info->pos = i;
  1525. list_append(info_list, sview_part_info);
  1526. sview_part_info->color_inx = i % sview_colors_cnt;
  1527. j2 = 0;
  1528. while (part_ptr->node_inx[j2] >= 0) {
  1529. int i2 = 0;
  1530. for(i2 = part_ptr->node_inx[j2];
  1531. i2 <= part_ptr->node_inx[j2+1];
  1532. i2++) {
  1533. node_ptr = &(node_info_ptr->node_array[i2]);
  1534. _insert_sview_part_sub(sview_part_info,
  1535. part_ptr,
  1536. node_ptr,
  1537. g_node_scaling);
  1538. }
  1539. j2 += 2;
  1540. }
  1541. list_sort(sview_part_info->sub_list,
  1542. (ListCmpF)_sview_sub_part_sort);
  1543. /* Need to do this after the fact so we deal with
  1544. complete sub parts.
  1545. */
  1546. itr = list_iterator_create(sview_part_info->sub_list);
  1547. while ((sview_part_sub = list_next(itr))) {
  1548. sview_part_info->sub_part_total.node_cnt +=
  1549. sview_part_sub->node_cnt;
  1550. sview_part_info->sub_part_total.cpu_alloc_cnt +=
  1551. sview_part_sub->cpu_alloc_cnt;
  1552. sview_part_info->sub_part_total.cpu_error_cnt +=
  1553. sview_part_sub->cpu_error_cnt;
  1554. sview_part_info->sub_part_total.cpu_idle_cnt +=
  1555. sview_part_sub->cpu_idle_cnt;
  1556. sview_part_info->sub_part_total.disk_total +=
  1557. sview_part_sub->disk_total;
  1558. sview_part_info->sub_part_total.mem_total +=
  1559. sview_part_sub->mem_total;
  1560. if (!sview_part_info->sub_part_total.features) {
  1561. /* store features and reasons
  1562. in the others group */
  1563. sview_part_info->sub_part_total.features
  1564. = sview_part_sub->features;
  1565. sview_part_info->sub_part_total.reason
  1566. = sview_part_sub->reason;
  1567. }
  1568. hostlist_sort(sview_part_sub->hl);
  1569. }
  1570. list_iterator_destroy(itr);
  1571. }
  1572. list_sort(info_list, (ListCmpF)_sview_part_sort_aval_dec);
  1573. return info_list;
  1574. }
  1575. static void _display_info_part(List info_list, popup_info_t *popup_win)
  1576. {
  1577. specific_info_t *spec_info = popup_win->spec_info;
  1578. char *name = (char *)spec_info->search_info->gchar_data;
  1579. int found = 0;
  1580. partition_info_t *part_ptr = NULL;
  1581. GtkTreeView *treeview = NULL;
  1582. ListIterator itr = NULL;
  1583. sview_part_info_t *sview_part_info = NULL;
  1584. int update = 0;
  1585. int j = 0;
  1586. if (!spec_info->search_info->gchar_data) {
  1587. //info = xstrdup("No pointer given!");
  1588. goto finished;
  1589. }
  1590. need_refresh:
  1591. if (!spec_info->display_widget) {
  1592. treeview = create_treeview_2cols_attach_to_table(
  1593. popup_win->table);
  1594. spec_info->display_widget =
  1595. gtk_widget_ref(GTK_WIDGET(treeview));
  1596. } else {
  1597. treeview = GTK_TREE_VIEW(spec_info->display_widget);
  1598. update = 1;
  1599. }
  1600. itr = list_iterator_create(info_list);
  1601. while ((sview_part_info = (sview_part_info_t*) list_next(itr))) {
  1602. part_ptr = sview_part_info->part_ptr;
  1603. if (!strcmp(part_ptr->name, name)) {
  1604. j = 0;
  1605. while (part_ptr->node_inx[j] >= 0) {
  1606. change_grid_color(
  1607. popup_win->grid_button_list,
  1608. part_ptr->node_inx[j],
  1609. part_ptr->node_inx[j+1],
  1610. sview_part_info->color_inx,
  1611. true, 0);
  1612. j += 2;
  1613. }
  1614. _layout_part_record(treeview, sview_part_info, update);
  1615. found = 1;
  1616. break;
  1617. }
  1618. }
  1619. list_iterator_destroy(itr);
  1620. post_setup_popup_grid_list(popup_win);
  1621. if (!found) {
  1622. if (!popup_win->not_found) {
  1623. char *temp = "PARTITION DOESN'T EXSIST\n";
  1624. GtkTreeIter iter;
  1625. GtkTreeModel *model = NULL;
  1626. /* only time this will be run so no update */
  1627. model = gtk_tree_view_get_model(treeview);
  1628. add_display_treestore_line(0,
  1629. GTK_TREE_STORE(model),
  1630. &iter,
  1631. temp, "");
  1632. }
  1633. popup_win->not_found = true;
  1634. } else {
  1635. if (popup_win->not_found) {
  1636. popup_win->not_found = false;
  1637. gtk_widget_destroy(spec_info->display_widget);
  1638. goto need_refresh;
  1639. }
  1640. }
  1641. gtk_widget_show(spec_info->display_widget);
  1642. finished:
  1643. return;
  1644. }
  1645. static void _process_each_partition(GtkTreeModel *model,
  1646. GtkTreePath *path,
  1647. GtkTreeIter *iter,
  1648. gpointer userdata)
  1649. {
  1650. char *type = userdata;
  1651. if (_DEBUG)
  1652. g_print("process_each_partition: global_multi_error = %d\n",
  1653. global_multi_error);
  1654. if (!global_multi_error) {
  1655. admin_part(model, iter, type);
  1656. }
  1657. }
  1658. /*process_each_partition ^^^*/
  1659. extern GtkWidget *create_part_entry(update_part_msg_t *part_msg,
  1660. GtkTreeModel *model, GtkTreeIter *iter)
  1661. {
  1662. GtkScrolledWindow *window = create_scrolled_window();
  1663. GtkBin *bin = NULL;
  1664. GtkViewport *view = NULL;
  1665. GtkTable *table = NULL;
  1666. int i = 0, row = 0;
  1667. display_data_t *display_data = create_data_part;
  1668. gtk_scrolled_window_set_policy(window,
  1669. GTK_POLICY_NEVER,
  1670. GTK_POLICY_AUTOMATIC);
  1671. bin = GTK_BIN(&window->container);
  1672. view = GTK_VIEWPORT(bin->child);
  1673. bin = GTK_BIN(&view->bin);
  1674. table = GTK_TABLE(bin->child);
  1675. gtk_table_resize(table, SORTID_CNT, 2);
  1676. gtk_table_set_homogeneous(table, FALSE);
  1677. for(i = 0; i < SORTID_CNT; i++) {
  1678. while (display_data++) {
  1679. if (display_data->id == -1)
  1680. break;
  1681. if (!display_data->name)
  1682. continue;
  1683. if (display_data->id != i)
  1684. continue;
  1685. display_admin_edit(
  1686. table, part_msg, &row, model, iter,
  1687. display_data,
  1688. G_CALLBACK(_admin_edit_combo_box_part),
  1689. G_CALLBACK(_admin_focus_out_part),
  1690. _set_active_combo_part);
  1691. break;
  1692. }
  1693. display_data = create_data_part;
  1694. }
  1695. gtk_table_resize(table, row, 2);
  1696. return GTK_WIDGET(window);
  1697. }
  1698. extern bool check_part_includes_node(int node_dx)
  1699. {
  1700. partition_info_t *part_ptr = NULL;
  1701. bool rc = FALSE;
  1702. int i = 0;
  1703. static partition_info_msg_t *part_info_ptr = NULL;
  1704. if (working_sview_config.show_hidden)
  1705. return TRUE;
  1706. if (!g_part_info_ptr)
  1707. i = get_new_info_part(&part_info_ptr, TRUE);
  1708. if (i && (i != SLURM_NO_CHANGE_IN_DATA)) {
  1709. if (_DEBUG)
  1710. g_print("check_part_includes_node : error %d ", i);
  1711. return FALSE;
  1712. }
  1713. for (i=0; i<g_part_info_ptr->record_count; i++) {
  1714. /* don't include allow group or hidden excludes */
  1715. part_ptr = &(g_part_info_ptr->partition_array[i]);
  1716. if (part_ptr->flags & PART_FLAG_HIDDEN)
  1717. continue;
  1718. if (part_ptr->node_inx[0] >= 0) {
  1719. if (_DEBUG) {
  1720. g_print("node_dx = %d ", node_dx);
  1721. g_print("part_node_inx[0] = %d ",
  1722. part_ptr->node_inx[0]);
  1723. g_print("part_node_inx[1] = %d \n",
  1724. part_ptr->node_inx[1]);
  1725. }
  1726. if (node_dx >= part_ptr->node_inx[0] &&
  1727. node_dx <= part_ptr->node_inx[1]) {
  1728. rc = TRUE;
  1729. if (_DEBUG)
  1730. g_print("hit!!\n");
  1731. }
  1732. }
  1733. if (rc)
  1734. break;
  1735. }
  1736. return rc;
  1737. }
  1738. extern void refresh_part(GtkAction *action, gpointer user_data)
  1739. {
  1740. popup_info_t *popup_win = (popup_info_t *)user_data;
  1741. xassert(popup_win);
  1742. xassert(popup_win->spec_info);
  1743. xassert(popup_win->spec_info->title);
  1744. popup_win->force_refresh = 1;
  1745. specific_info_part(popup_win);
  1746. }
  1747. extern bool visible_part(char* part_name)
  1748. {
  1749. static partition_info_msg_t *part_info_ptr = NULL;
  1750. partition_info_t *m_part_ptr = NULL;
  1751. int i;
  1752. int rc = FALSE;
  1753. if (!g_part_info_ptr)
  1754. get_new_info_part(&part_info_ptr, force_refresh);
  1755. for (i=0; i<g_part_info_ptr->record_count; i++) {
  1756. m_part_ptr = &(g_part_info_ptr->partition_array[i]);
  1757. if (!strcmp(m_part_ptr->name, part_name)) {
  1758. if (m_part_ptr->flags & PART_FLAG_HIDDEN)
  1759. rc = FALSE;
  1760. else
  1761. rc = TRUE;
  1762. }
  1763. }
  1764. return rc;
  1765. }
  1766. extern int get_new_info_part(partition_info_msg_t **part_ptr, int force)
  1767. {
  1768. static partition_info_msg_t *new_part_ptr = NULL;
  1769. uint16_t show_flags = 0;
  1770. int error_code = SLURM_NO_CHANGE_IN_DATA;
  1771. time_t now = time(NULL);
  1772. static time_t last;
  1773. static bool changed = 0;
  1774. static uint16_t last_flags = 0;
  1775. if (g_part_info_ptr && !force
  1776. && ((now - last) < working_sview_config.refresh_delay)) {
  1777. if (*part_ptr != g_part_info_ptr)
  1778. error_code = SLURM_SUCCESS;
  1779. *part_ptr = g_part_info_ptr;
  1780. if (changed)
  1781. error_code = SLURM_SUCCESS;
  1782. goto end_it;
  1783. }
  1784. last = now;
  1785. if (working_sview_config.show_hidden)
  1786. /*ignore 'AllowGroups, Hidden settings*/
  1787. show_flags |= SHOW_ALL;
  1788. if (g_part_info_ptr) {
  1789. if (show_flags != last_flags)
  1790. g_part_info_ptr->last_update = 0;
  1791. error_code = slurm_load_partitions(g_part_info_ptr->last_update,
  1792. &new_part_ptr, show_flags);
  1793. if (error_code == SLURM_SUCCESS) {
  1794. slurm_free_partition_info_msg(g_part_info_ptr);
  1795. changed = 1;
  1796. } else if (slurm_get_errno() == SLURM_NO_CHANGE_IN_DATA) {
  1797. error_code = SLURM_NO_CHANGE_IN_DATA;
  1798. new_part_ptr = g_part_info_ptr;
  1799. changed = 0;
  1800. }
  1801. } else {
  1802. new_part_ptr = NULL;
  1803. error_code = slurm_load_partitions((time_t) NULL, &new_part_ptr,
  1804. show_flags);
  1805. changed = 1;
  1806. }
  1807. last_flags = show_flags;
  1808. g_part_info_ptr = new_part_ptr;
  1809. if (g_part_info_ptr && (*part_ptr != g_part_info_ptr))
  1810. error_code = SLURM_SUCCESS;
  1811. *part_ptr = new_part_ptr;
  1812. end_it:
  1813. return error_code;
  1814. }
  1815. static GtkListStore *_create_model_part2(int type)
  1816. {
  1817. GtkListStore *model = NULL;
  1818. GtkTreeIter iter;
  1819. switch (type) {
  1820. case SORTID_DEFAULT:
  1821. case SORTID_HIDDEN:
  1822. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1823. gtk_list_store_append(model, &iter);
  1824. gtk_list_store_set(model, &iter,
  1825. 0, "no (default)", 1, SORTID_DEFAULT, -1);
  1826. gtk_list_store_append(model, &iter);
  1827. gtk_list_store_set(model, &iter,
  1828. 0, "yes", 1, SORTID_DEFAULT, -1);
  1829. break;
  1830. case SORTID_ROOT:
  1831. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1832. gtk_list_store_append(model, &iter);
  1833. gtk_list_store_set(model, &iter,
  1834. 0, "yes (default)", 1, SORTID_DEFAULT, -1);
  1835. gtk_list_store_append(model, &iter);
  1836. gtk_list_store_set(model, &iter,
  1837. 0, "no", 1, SORTID_DEFAULT, -1);
  1838. break;
  1839. case SORTID_SHARE:
  1840. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1841. gtk_list_store_append(model, &iter);
  1842. gtk_list_store_set(model, &iter,
  1843. 0, "no (default)", 1, SORTID_SHARE, -1);
  1844. gtk_list_store_append(model, &iter);
  1845. gtk_list_store_set(model, &iter,
  1846. 0, "yes", 1, SORTID_SHARE, -1);
  1847. gtk_list_store_append(model, &iter);
  1848. gtk_list_store_set(model, &iter,
  1849. 0, "force", 1, SORTID_SHARE, -1);
  1850. gtk_list_store_append(model, &iter);
  1851. gtk_list_store_set(model, &iter,
  1852. 0, "exclusive", 1, SORTID_SHARE, -1);
  1853. break;
  1854. case SORTID_PART_STATE:
  1855. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1856. gtk_list_store_append(model, &iter);
  1857. gtk_list_store_set(model, &iter,
  1858. 0, "up (default)", 1, SORTID_PART_STATE, -1);
  1859. gtk_list_store_append(model, &iter);
  1860. gtk_list_store_set(model, &iter,
  1861. 0, "down", 1, SORTID_PART_STATE, -1);
  1862. gtk_list_store_append(model, &iter);
  1863. gtk_list_store_set(model, &iter,
  1864. 0, "inactive", 1, SORTID_PART_STATE, -1);
  1865. gtk_list_store_append(model, &iter);
  1866. gtk_list_store_set(model, &iter,
  1867. 0, "drain", 1, SORTID_PART_STATE, -1);
  1868. break;
  1869. case SORTID_PREEMPT_MODE:
  1870. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1871. gtk_list_store_append(model, &iter);
  1872. gtk_list_store_set(model, &iter, 0,
  1873. preempt_mode_string(slurm_get_preempt_mode()),
  1874. 1, SORTID_PREEMPT_MODE, -1);
  1875. gtk_list_store_append(model, &iter);
  1876. gtk_list_store_set(model, &iter,
  1877. 0, "cancel", 1, SORTID_PREEMPT_MODE, -1);
  1878. gtk_list_store_append(model, &iter);
  1879. gtk_list_store_set(model, &iter,
  1880. 0, "checkpoint", 1, SORTID_PREEMPT_MODE,-1);
  1881. gtk_list_store_append(model, &iter);
  1882. gtk_list_store_set(model, &iter,
  1883. 0, "off", 1, SORTID_PREEMPT_MODE, -1);
  1884. gtk_list_store_append(model, &iter);
  1885. gtk_list_store_set(model, &iter,
  1886. 0, "requeue", 1, SORTID_PREEMPT_MODE, -1);
  1887. gtk_list_store_append(model, &iter);
  1888. gtk_list_store_set(model, &iter,
  1889. 0, "suspend", 1, SORTID_PREEMPT_MODE, -1);
  1890. break;
  1891. }
  1892. return model;
  1893. }
  1894. extern GtkListStore *create_model_part(int type)
  1895. {
  1896. GtkListStore *model = NULL;
  1897. GtkTreeIter iter;
  1898. char *upper = NULL, *lower = NULL;
  1899. int i = 0;
  1900. switch (type) {
  1901. case SORTID_DEFAULT:
  1902. case SORTID_HIDDEN:
  1903. case SORTID_ROOT:
  1904. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1905. gtk_list_store_append(model, &iter);
  1906. gtk_list_store_set(model, &iter,
  1907. 0, "yes", 1, type, -1);
  1908. gtk_list_store_append(model, &iter);
  1909. gtk_list_store_set(model, &iter,
  1910. 0, "no", 1, type, -1);
  1911. break;
  1912. case SORTID_PREEMPT_MODE:
  1913. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1914. gtk_list_store_append(model, &iter);
  1915. gtk_list_store_set(model, &iter,
  1916. 0, "cancel", 1, SORTID_PREEMPT_MODE, -1);
  1917. gtk_list_store_append(model, &iter);
  1918. gtk_list_store_set(model, &iter,
  1919. 0, "checkpoint", 1, SORTID_PREEMPT_MODE,-1);
  1920. gtk_list_store_append(model, &iter);
  1921. gtk_list_store_set(model, &iter,
  1922. 0, "off", 1, SORTID_PREEMPT_MODE, -1);
  1923. gtk_list_store_append(model, &iter);
  1924. gtk_list_store_set(model, &iter,
  1925. 0, "requeue", 1, SORTID_PREEMPT_MODE, -1);
  1926. gtk_list_store_append(model, &iter);
  1927. gtk_list_store_set(model, &iter,
  1928. 0, "suspend", 1, SORTID_PREEMPT_MODE, -1);
  1929. break;
  1930. case SORTID_GRACE_TIME:
  1931. case SORTID_PRIORITY:
  1932. case SORTID_TIMELIMIT:
  1933. case SORTID_NODES_MIN:
  1934. case SORTID_NODES_MAX:
  1935. break;
  1936. case SORTID_SHARE:
  1937. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1938. gtk_list_store_append(model, &iter);
  1939. gtk_list_store_set(model, &iter,
  1940. 0, "force", 1, SORTID_SHARE, -1);
  1941. gtk_list_store_append(model, &iter);
  1942. gtk_list_store_set(model, &iter,
  1943. 0, "no", 1, SORTID_SHARE, -1);
  1944. gtk_list_store_append(model, &iter);
  1945. gtk_list_store_set(model, &iter,
  1946. 0, "yes", 1, SORTID_SHARE, -1);
  1947. gtk_list_store_append(model, &iter);
  1948. gtk_list_store_set(model, &iter,
  1949. 0, "exclusive", 1, SORTID_SHARE, -1);
  1950. break;
  1951. case SORTID_GROUPS:
  1952. break;
  1953. case SORTID_NODELIST:
  1954. break;
  1955. case SORTID_PART_STATE:
  1956. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1957. gtk_list_store_append(model, &iter);
  1958. gtk_list_store_set(model, &iter,
  1959. 0, "up", 1, SORTID_PART_STATE, -1);
  1960. gtk_list_store_append(model, &iter);
  1961. gtk_list_store_set(model, &iter,
  1962. 0, "down", 1, SORTID_PART_STATE, -1);
  1963. gtk_list_store_append(model, &iter);
  1964. gtk_list_store_set(model, &iter,
  1965. 0, "inactive", 1, SORTID_PART_STATE, -1);
  1966. gtk_list_store_append(model, &iter);
  1967. gtk_list_store_set(model, &iter,
  1968. 0, "drain", 1, SORTID_PART_STATE, -1);
  1969. break;
  1970. case SORTID_NODE_STATE:
  1971. model = gtk_list_store_new(2, G_TYPE_STRING, G_TYPE_INT);
  1972. gtk_list_store_append(model, &iter);
  1973. gtk_list_store_set(model, &iter,
  1974. 0, "drain", 1, SORTID_NODE_STATE, -1);
  1975. gtk_list_store_append(model, &iter);
  1976. gtk_list_store_set(model, &iter,
  1977. 0, "resume", 1, SORTID_NODE_STATE, -1);
  1978. for(i = 0; i < NODE_STATE_END; i++) {
  1979. upper = node_state_string(i);
  1980. if (!strcmp(upper, "UNKNOWN"))
  1981. continue;
  1982. gtk_list_store_append(model, &iter);
  1983. lower = str_tolower(upper);
  1984. gtk_list_store_set(model, &iter,
  1985. 0, lower, 1, SORTID_NODE_STATE, -1);
  1986. xfree(lower);
  1987. }
  1988. break;
  1989. }
  1990. return model;
  1991. }
  1992. extern void admin_edit_part(GtkCellRendererText *cell,
  1993. const char *path_string,
  1994. const char *new_text,
  1995. gpointer data)
  1996. {
  1997. GtkTreeStore *treestore = GTK_TREE_STORE(data);
  1998. GtkTreePath *path = gtk_tree_path_new_from_string(path_string);
  1999. GtkTreeIter iter;
  2000. update_part_msg_t *part_msg = xmalloc(sizeof(update_part_msg_t));
  2001. char *temp = NULL;
  2002. char *old_text = NULL;
  2003. const char *type = NULL;
  2004. int column = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(cell),
  2005. "column"));
  2006. if (!new_text || !strcmp(new_text, ""))
  2007. goto no_input;
  2008. gtk_tree_model_get_iter(GTK_TREE_MODEL(treestore), &iter, path);
  2009. if (column != SORTID_NODE_STATE) {
  2010. slurm_init_part_desc_msg(part_msg);
  2011. gtk_tree_model_get(GTK_TREE_MODEL(treestore), &iter,
  2012. SORTID_NAME, &temp,
  2013. column, &old_text,
  2014. -1);
  2015. part_msg->name = xstrdup(temp);
  2016. g_free(temp);
  2017. }
  2018. type = _set_part_msg(part_msg, new_text, column);
  2019. if (global_edit_error)
  2020. goto print_error;
  2021. if (got_edit_signal) {
  2022. temp = got_edit_signal;
  2023. got_edit_signal = NULL;
  2024. admin_part(GTK_TREE_MODEL(treestore), &iter, temp);
  2025. xfree(temp);
  2026. goto no_input;
  2027. }
  2028. if (got_features_edit_signal) {
  2029. admin_part(GTK_TREE_MODEL(treestore), &iter, (char *)type);
  2030. goto no_input;
  2031. }
  2032. if (column != SORTID_NODE_STATE && column != SORTID_FEATURES ) {
  2033. if (old_text && !strcmp(old_text, new_text)) {
  2034. temp = g_strdup_printf("No change in value.");
  2035. } else if (slurm_update_partition(part_msg)
  2036. == SLURM_SUCCESS) {
  2037. gtk_tree_store_set(treestore, &iter, column,
  2038. new_text, -1);
  2039. temp = g_strdup_printf("Partition %s %s changed to %s",
  2040. part_msg->name,
  2041. type,
  2042. new_text);
  2043. } else {
  2044. print_error:
  2045. temp = g_strdup_printf("Partition %s %s can't be "
  2046. "set to %s",
  2047. part_msg->name,
  2048. type,
  2049. new_text);
  2050. }
  2051. display_edit_note(temp);
  2052. g_free(temp);
  2053. }
  2054. no_input:
  2055. slurm_free_update_part_msg(part_msg);
  2056. gtk_tree_path_free (path);
  2057. g_free(old_text);
  2058. g_static_mutex_unlock(&sview_mutex);
  2059. }
  2060. extern void get_info_part(GtkTable *table, display_data_t *display_data)
  2061. {
  2062. int part_error_code = SLURM_SUCCESS;
  2063. int node_error_code = SLURM_SUCCESS;
  2064. static int view = -1;
  2065. static partition_info_msg_t *part_info_ptr = NULL;
  2066. static node_info_msg_t *node_info_ptr = NULL;
  2067. char error_char[100];
  2068. GtkWidget *label = NULL;
  2069. GtkTreeView *tree_view = NULL;
  2070. static GtkWidget *display_widget = NULL;
  2071. List info_list = NULL;
  2072. int j, k;
  2073. sview_part_info_t *sview_part_info = NULL;
  2074. partition_info_t *part_ptr = NULL;
  2075. ListIterator itr = NULL;
  2076. GtkTreePath *path = NULL;
  2077. static bool set_opts = FALSE;
  2078. if (!set_opts)
  2079. set_page_opts(PART_PAGE, display_data_part,
  2080. SORTID_CNT, _initial_page_opts);
  2081. set_opts = TRUE;
  2082. /* reset */
  2083. if (!table && !display_data) {
  2084. if (display_widget)
  2085. gtk_widget_destroy(display_widget);
  2086. display_widget = NULL;
  2087. part_info_ptr = NULL;
  2088. node_info_ptr = NULL;
  2089. goto reset_curs;
  2090. }
  2091. if (display_data)
  2092. local_display_data = display_data;
  2093. if (!table) {
  2094. display_data_part->set_menu = local_display_data->set_menu;
  2095. goto reset_curs;
  2096. }
  2097. if (display_widget && toggled) {
  2098. gtk_widget_destroy(display_widget);
  2099. display_widget = NULL;
  2100. goto display_it;
  2101. }
  2102. if ((part_error_code = get_new_info_part(&part_info_ptr, force_refresh))
  2103. == SLURM_NO_CHANGE_IN_DATA) {
  2104. // just goto the new info node
  2105. } else if (part_error_code != SLURM_SUCCESS) {
  2106. if (view == ERROR_VIEW)
  2107. goto end_it;
  2108. if (display_widget)
  2109. gtk_widget_destroy(display_widget);
  2110. view = ERROR_VIEW;
  2111. snprintf(error_char, 100, "slurm_load_partitions: %s",
  2112. slurm_strerror(slurm_get_errno()));
  2113. label = gtk_label_new(error_char);
  2114. display_widget = gtk_widget_ref(GTK_WIDGET(label));
  2115. gtk_table_attach_defaults(table, label, 0, 1, 0, 1);
  2116. gtk_widget_show(label);
  2117. goto end_it;
  2118. }
  2119. if ((node_error_code = get_new_info_node(&node_info_ptr, force_refresh))
  2120. == SLURM_NO_CHANGE_IN_DATA) {
  2121. if ((!display_widget || view == ERROR_VIEW)
  2122. || (part_error_code != SLURM_NO_CHANGE_IN_DATA))
  2123. goto display_it;
  2124. } else if (node_error_code != SLURM_SUCCESS) {
  2125. if (view == ERROR_VIEW)
  2126. goto end_it;
  2127. if (display_widget)
  2128. gtk_widget_destroy(display_widget);
  2129. view = ERROR_VIEW;
  2130. snprintf(error_char, 100, "slurm_load_node: %s",
  2131. slurm_strerror(slurm_get_errno()));
  2132. label = gtk_label_new(error_char);
  2133. display_widget = gtk_widget_ref(GTK_WIDGET(label));
  2134. gtk_table_attach_defaults(table, label, 0, 1, 0, 1);
  2135. gtk_widget_show(label);
  2136. goto end_it;
  2137. }
  2138. display_it:
  2139. info_list = _create_part_info_list(part_info_ptr, node_info_ptr);
  2140. if (!info_list)
  2141. goto reset_curs;
  2142. /* set up the grid */
  2143. if (display_widget && GTK_IS_TREE_VIEW(display_widget)
  2144. && gtk_tree_selection_count_selected_rows(
  2145. gtk_tree_view_get_selection(
  2146. GTK_TREE_VIEW(display_widget)))) {
  2147. GtkTreeViewColumn *focus_column = NULL;
  2148. /* highlight the correct nodes from the last selection */
  2149. gtk_tree_view_get_cursor(GTK_TREE_VIEW(display_widget),
  2150. &path, &focus_column);
  2151. }
  2152. if (!path) {
  2153. int array_size = node_info_ptr->record_count;
  2154. int *color_inx = xmalloc(sizeof(int) * array_size);
  2155. bool *color_set_flag = xmalloc(sizeof(bool) * array_size);
  2156. itr = list_iterator_create(info_list);
  2157. while ((sview_part_info = list_next(itr))) {
  2158. part_ptr = sview_part_info->part_ptr;
  2159. j = 0;
  2160. while (part_ptr->node_inx[j] >= 0) {
  2161. for (k = part_ptr->node_inx[j];
  2162. k <= part_ptr->node_inx[j+1]; k++) {
  2163. color_set_flag[k] = true;
  2164. color_inx[k] = sview_part_info->
  2165. color_inx;
  2166. }
  2167. j += 2;
  2168. }
  2169. }
  2170. list_iterator_destroy(itr);
  2171. change_grid_color_array(grid_button_list, array_size,
  2172. color_inx, color_set_flag, true, 0);
  2173. change_grid_color(grid_button_list, -1, -1,
  2174. MAKE_WHITE, true, 0);
  2175. xfree(color_inx);
  2176. xfree(color_set_flag);
  2177. } else
  2178. highlight_grid(GTK_TREE_VIEW(display_widget),
  2179. SORTID_NODE_INX, SORTID_COLOR_INX,
  2180. grid_button_list);
  2181. if (view == ERROR_VIEW && display_widget) {
  2182. gtk_widget_destroy(display_widget);
  2183. display_widget = NULL;
  2184. }
  2185. if (!display_widget) {
  2186. tree_view = create_treeview(local_display_data,
  2187. &grid_button_list);
  2188. /*set multiple capability here*/
  2189. gtk_tree_selection_set_mode(
  2190. gtk_tree_view_get_selection(tree_view),
  2191. GTK_SELECTION_MULTIPLE);
  2192. display_widget = gtk_widget_ref(GTK_WIDGET(tree_view));
  2193. gtk_table_attach_defaults(table,
  2194. GTK_WIDGET(tree_view),
  2195. 0, 1, 0, 1);
  2196. /* since this function sets the model of the tree_view
  2197. to the treestore we don't really care about
  2198. the return value */
  2199. create_treestore(tree_view, display_data_part,
  2200. SORTID_CNT, SORTID_NAME, SORTID_COLOR);
  2201. }
  2202. view = INFO_VIEW;
  2203. _update_info_part(info_list, GTK_TREE_VIEW(display_widget));
  2204. end_it:
  2205. toggled = FALSE;
  2206. force_refresh = FALSE;
  2207. reset_curs:
  2208. if (main_window && main_window->window)
  2209. gdk_window_set_cursor(main_window->window, NULL);
  2210. return;
  2211. }
  2212. extern void specific_info_part(popup_info_t *popup_win)
  2213. {
  2214. int part_error_code = SLURM_SUCCESS;
  2215. int node_error_code = SLURM_SUCCESS;
  2216. static partition_info_msg_t *part_info_ptr = NULL;
  2217. static node_info_msg_t *node_info_ptr = NULL;
  2218. specific_info_t *spec_info = popup_win->spec_info;
  2219. char error_char[100];
  2220. GtkWidget *label = NULL;
  2221. GtkTreeView *tree_view = NULL;
  2222. List info_list = NULL;
  2223. List send_info_list = NULL;
  2224. int j=0, i=-1;
  2225. sview_part_info_t *sview_part_info_ptr = NULL;
  2226. partition_info_t *part_ptr = NULL;
  2227. ListIterator itr = NULL;
  2228. hostset_t hostset = NULL;
  2229. if (!spec_info->display_widget)
  2230. setup_popup_info(popup_win, display_data_part, SORTID_CNT);
  2231. if (spec_info->display_widget && popup_win->toggled) {
  2232. gtk_widget_destroy(spec_info->display_widget);
  2233. spec_info->display_widget = NULL;
  2234. goto display_it;
  2235. }
  2236. if ((part_error_code = get_new_info_part(&part_info_ptr,
  2237. popup_win->force_refresh))
  2238. == SLURM_NO_CHANGE_IN_DATA) {
  2239. } else if (part_error_code != SLURM_SUCCESS) {
  2240. if (spec_info->view == ERROR_VIEW)
  2241. goto end_it;
  2242. if (spec_info->display_widget) {
  2243. gtk_widget_destroy(spec_info->display_widget);
  2244. spec_info->display_widget = NULL;
  2245. }
  2246. spec_info->view = ERROR_VIEW;
  2247. snprintf(error_char, 100, "slurm_load_partitions: %s",
  2248. slurm_strerror(slurm_get_errno()));
  2249. label = gtk_label_new(error_char);
  2250. spec_info->display_widget = gtk_widget_ref(GTK_WIDGET(label));
  2251. gtk_table_attach_defaults(popup_win->table, label, 0, 1, 0, 1);
  2252. gtk_widget_show(label);
  2253. goto end_it;
  2254. }
  2255. if ((node_error_code = get_new_info_node(&node_info_ptr,
  2256. popup_win->force_refresh))
  2257. == SLURM_NO_CHANGE_IN_DATA) {
  2258. if ((!spec_info->display_widget
  2259. || spec_info->view == ERROR_VIEW)
  2260. || (part_error_code != SLURM_NO_CHANGE_IN_DATA))
  2261. goto display_it;
  2262. } else if (node_error_code != SLURM_SUCCESS) {
  2263. if (spec_info->view == ERROR_VIEW)
  2264. goto end_it;
  2265. if (spec_info->display_widget)
  2266. gtk_widget_destroy(spec_info->display_widget);
  2267. spec_info->view = ERROR_VIEW;
  2268. snprintf(error_char, 100, "slurm_load_node: %s",
  2269. slurm_strerror(slurm_get_errno()));
  2270. label = gtk_label_new(error_char);
  2271. spec_info->display_widget = gtk_widget_ref(GTK_WIDGET(label));
  2272. gtk_table_attach_defaults(popup_win->table, label, 0, 1, 0, 1);
  2273. gtk_widget_show(label);
  2274. goto end_it;
  2275. }
  2276. display_it:
  2277. info_list = _create_part_info_list(part_info_ptr, node_info_ptr);
  2278. if (!info_list)
  2279. return;
  2280. if (spec_info->view == ERROR_VIEW && spec_info->display_widget) {
  2281. gtk_widget_destroy(spec_info->display_widget);
  2282. spec_info->display_widget = NULL;
  2283. }
  2284. if (spec_info->type != INFO_PAGE && !spec_info->display_widget) {
  2285. tree_view = create_treeview(local_display_data,
  2286. &popup_win->grid_button_list);
  2287. /*set multiple capability here*/
  2288. gtk_tree_selection_set_mode(
  2289. gtk_tree_view_get_selection(tree_view),
  2290. GTK_SELECTION_MULTIPLE);
  2291. spec_info->display_widget =
  2292. gtk_widget_ref(GTK_WIDGET(tree_view));
  2293. gtk_table_attach_defaults(popup_win->table,
  2294. GTK_WIDGET(tree_view),
  2295. 0, 1, 0, 1);
  2296. /* since this function sets the model of the tree_view
  2297. to the treestore we don't really care about
  2298. the return value */
  2299. create_treestore(tree_view, popup_win->display_data,
  2300. SORTID_CNT, SORTID_NAME, SORTID_COLOR);
  2301. }
  2302. setup_popup_grid_list(popup_win);
  2303. spec_info->view = INFO_VIEW;
  2304. if (spec_info->type == INFO_PAGE) {
  2305. _display_info_part(info_list, popup_win);
  2306. goto end_it;
  2307. }
  2308. /* just linking to another list, don't free the inside, just
  2309. the list */
  2310. send_info_list = list_create(NULL);
  2311. itr = list_iterator_create(info_list);
  2312. i = -1;
  2313. while ((sview_part_info_ptr = list_next(itr))) {
  2314. i++;
  2315. part_ptr = sview_part_info_ptr->part_ptr;
  2316. switch(spec_info->type) {
  2317. case RESV_PAGE:
  2318. case NODE_PAGE:
  2319. if (!part_ptr->nodes)
  2320. continue;
  2321. if (!(hostset = hostset_create(
  2322. spec_info->search_info->gchar_data)))
  2323. continue;
  2324. if (!hostset_intersects(hostset, part_ptr->nodes)) {
  2325. hostset_destroy(hostset);
  2326. continue;
  2327. }
  2328. hostset_destroy(hostset);
  2329. break;
  2330. case PART_PAGE:
  2331. switch(spec_info->search_info->search_type) {
  2332. case SEARCH_PARTITION_NAME:
  2333. if (!spec_info->search_info->gchar_data)
  2334. continue;
  2335. if (strcmp(part_ptr->name,
  2336. spec_info->search_info->gchar_data))
  2337. continue;
  2338. break;
  2339. case SEARCH_PARTITION_STATE:
  2340. if (spec_info->search_info->int_data == NO_VAL)
  2341. continue;
  2342. if (part_ptr->state_up !=
  2343. spec_info->search_info->int_data)
  2344. continue;
  2345. break;
  2346. default:
  2347. continue;
  2348. break;
  2349. }
  2350. break;
  2351. case BLOCK_PAGE:
  2352. case JOB_PAGE:
  2353. if (!spec_info->search_info->gchar_data)
  2354. continue;
  2355. if (strcmp(part_ptr->name,
  2356. spec_info->search_info->gchar_data))
  2357. continue;
  2358. break;
  2359. default:
  2360. g_print("Unknown type %d\n", spec_info->type);
  2361. list_iterator_destroy(itr);
  2362. goto end_it;
  2363. }
  2364. list_push(send_info_list, sview_part_info_ptr);
  2365. j=0;
  2366. while (part_ptr->node_inx[j] >= 0) {
  2367. change_grid_color(
  2368. popup_win->grid_button_list,
  2369. part_ptr->node_inx[j],
  2370. part_ptr->node_inx[j+1],
  2371. sview_part_info_ptr->color_inx, true, 0);
  2372. j += 2;
  2373. }
  2374. }
  2375. list_iterator_destroy(itr);
  2376. post_setup_popup_grid_list(popup_win);
  2377. _update_info_part(send_info_list,
  2378. GTK_TREE_VIEW(spec_info->display_widget));
  2379. list_destroy(send_info_list);
  2380. end_it:
  2381. popup_win->toggled = 0;
  2382. popup_win->force_refresh = 0;
  2383. return;
  2384. }
  2385. extern void set_menus_part(void *arg, void *arg2, GtkTreePath *path, int type)
  2386. {
  2387. GtkTreeView *tree_view = (GtkTreeView *)arg;
  2388. popup_info_t *popup_win = (popup_info_t *)arg;
  2389. GtkMenu *menu = (GtkMenu *)arg2;
  2390. List button_list = (List)arg2;
  2391. switch(type) {
  2392. case TAB_CLICKED:
  2393. make_fields_menu(NULL, menu, display_data_part, SORTID_CNT);
  2394. break;
  2395. case ROW_CLICKED:
  2396. make_options_menu(tree_view, path, menu, options_data_part);
  2397. break;
  2398. case ROW_LEFT_CLICKED:
  2399. highlight_grid(tree_view, SORTID_NODE_INX,
  2400. SORTID_COLOR_INX, button_list);
  2401. break;
  2402. case FULL_CLICKED:
  2403. {
  2404. GtkTreeModel *model = gtk_tree_view_get_model(tree_view);
  2405. GtkTreeIter iter;
  2406. if (!gtk_tree_model_get_iter(model, &iter, path)) {
  2407. g_error("error getting iter from model\n");
  2408. break;
  2409. }
  2410. popup_all_part(model, &iter, INFO_PAGE);
  2411. break;
  2412. }
  2413. case POPUP_CLICKED:
  2414. make_fields_menu(popup_win, menu,
  2415. popup_win->display_data, SORTID_CNT);
  2416. break;
  2417. default:
  2418. g_error("UNKNOWN type %d given to set_fields\n", type);
  2419. }
  2420. }
  2421. extern void popup_all_part(GtkTreeModel *model, GtkTreeIter *iter, int id)
  2422. {
  2423. char *name = NULL;
  2424. char *state = NULL;
  2425. char title[100];
  2426. int only_line = 0;
  2427. ListIterator itr = NULL;
  2428. popup_info_t *popup_win = NULL;
  2429. GError *error = NULL;
  2430. GtkTreeIter par_iter;
  2431. gtk_tree_model_get(model, iter, SORTID_NAME, &name, -1);
  2432. switch(id) {
  2433. case JOB_PAGE:
  2434. snprintf(title, 100, "Job(s) in partition %s", name);
  2435. break;
  2436. case RESV_PAGE:
  2437. snprintf(title, 100, "Reservation(s) in partition %s", name);
  2438. break;
  2439. case NODE_PAGE:
  2440. gtk_tree_model_get(model, iter, SORTID_ONLY_LINE,
  2441. &only_line, -1);
  2442. if (!only_line)
  2443. gtk_tree_model_get(model, iter,
  2444. SORTID_NODE_STATE, &state, -1);
  2445. if (cluster_flags & CLUSTER_FLAG_BG) {
  2446. if (!state || !strlen(state))
  2447. snprintf(title, 100,
  2448. "Midplane(s) in partition %s",
  2449. name);
  2450. else
  2451. snprintf(title, 100,
  2452. "Midplane(s) in partition %s "
  2453. "that are in '%s' state",
  2454. name, state);
  2455. } else {
  2456. if (!state || !strlen(state))
  2457. snprintf(title, 100, "Node(s) in partition %s ",
  2458. name);
  2459. else
  2460. snprintf(title, 100,
  2461. "Node(s) in partition %s that are in "
  2462. "'%s' state",
  2463. name, state);
  2464. }
  2465. break;
  2466. case BLOCK_PAGE:
  2467. snprintf(title, 100, "Block(s) in partition %s", name);
  2468. break;
  2469. case SUBMIT_PAGE:
  2470. snprintf(title, 100, "Submit job in partition %s", name);
  2471. break;
  2472. case INFO_PAGE:
  2473. snprintf(title, 100, "Full info for partition %s", name);
  2474. break;
  2475. default:
  2476. g_print("part got %d\n", id);
  2477. }
  2478. itr = list_iterator_create(popup_list);
  2479. while ((popup_win = list_next(itr))) {
  2480. if (popup_win->spec_info)
  2481. if (!strcmp(popup_win->spec_info->title, title)) {
  2482. break;
  2483. }
  2484. }
  2485. list_iterator_destroy(itr);
  2486. if (!popup_win) {
  2487. if (id == INFO_PAGE)
  2488. popup_win = create_popup_info(id, PART_PAGE, title);
  2489. else
  2490. popup_win = create_popup_info(PART_PAGE, id, title);
  2491. } else {
  2492. g_free(name);
  2493. g_free(state);
  2494. gtk_window_present(GTK_WINDOW(popup_win->popup));
  2495. return;
  2496. }
  2497. /* Pass the model and the structs from the iter so we can always get
  2498. the current node_inx.
  2499. */
  2500. popup_win->model = model;
  2501. popup_win->iter = *iter;
  2502. popup_win->node_inx_id = SORTID_NODE_INX;
  2503. switch(id) {
  2504. case JOB_PAGE:
  2505. case BLOCK_PAGE:
  2506. case INFO_PAGE:
  2507. popup_win->spec_info->search_info->gchar_data = name;
  2508. //specific_info_job(popup_win);
  2509. break;
  2510. case RESV_PAGE:
  2511. case NODE_PAGE:
  2512. g_free(name);
  2513. /* we want to include the parent's nodes here not just
  2514. the subset */
  2515. if (gtk_tree_model_iter_parent(model, &par_iter, iter))
  2516. gtk_tree_model_get(model, &par_iter,
  2517. SORTID_NODELIST, &name, -1);
  2518. else
  2519. gtk_tree_model_get(model, iter,
  2520. SORTID_NODELIST, &name, -1);
  2521. popup_win->spec_info->search_info->gchar_data = name;
  2522. if (state && strlen(state)) {
  2523. popup_win->spec_info->search_info->search_type =
  2524. SEARCH_NODE_STATE;
  2525. gtk_tree_model_get(
  2526. model, iter, SORTID_NODE_STATE_NUM,
  2527. &popup_win->spec_info->search_info->int_data,
  2528. -1);
  2529. } else {
  2530. popup_win->spec_info->search_info->search_type =
  2531. SEARCH_NODE_NAME;
  2532. }
  2533. g_free(state);
  2534. //specific_info_node(popup_win);
  2535. break;
  2536. case SUBMIT_PAGE:
  2537. break;
  2538. default:
  2539. g_print("part got unknown type %d\n", id);
  2540. }
  2541. if (!sview_thread_new((gpointer)popup_thr, popup_win, FALSE, &error)) {
  2542. g_printerr ("Failed to create part popup thread: %s\n",
  2543. error->message);
  2544. return;
  2545. }
  2546. }
  2547. extern void select_admin_partitions(GtkTreeModel *model,
  2548. GtkTreeIter *iter,
  2549. display_data_t *display_data,
  2550. GtkTreeView *treeview)
  2551. {
  2552. if (treeview) {
  2553. if (display_data->extra & EXTRA_NODES) {
  2554. select_admin_nodes(model, iter, display_data,
  2555. SORTID_NODELIST, treeview);
  2556. return;
  2557. }
  2558. global_multi_error = FALSE;
  2559. gtk_tree_selection_selected_foreach(
  2560. gtk_tree_view_get_selection(treeview),
  2561. _process_each_partition, display_data->name);
  2562. }
  2563. } /*select_admin_partitions ^^^*/
  2564. extern void admin_part(GtkTreeModel *model, GtkTreeIter *iter, char *type)
  2565. {
  2566. char *nodelist = NULL;
  2567. char *partid = NULL;
  2568. update_part_msg_t *part_msg = xmalloc(sizeof(update_part_msg_t));
  2569. int edit_type = 0;
  2570. int response = 0;
  2571. char tmp_char[100];
  2572. char *temp = NULL;
  2573. GtkWidget *label = NULL;
  2574. GtkWidget *entry = NULL;
  2575. GtkWidget *popup = gtk_dialog_new_with_buttons(
  2576. type,
  2577. GTK_WINDOW(main_window),
  2578. GTK_DIALOG_MODAL | GTK_DIALOG_DESTROY_WITH_PARENT,
  2579. NULL);
  2580. gtk_window_set_transient_for(GTK_WINDOW(popup), NULL);
  2581. gtk_tree_model_get(model, iter, SORTID_NAME, &partid, -1);
  2582. gtk_tree_model_get(model, iter, SORTID_NODELIST, &nodelist, -1);
  2583. slurm_init_part_desc_msg(part_msg);
  2584. part_msg->name = xstrdup(partid);
  2585. if (!strcasecmp("Change Partition State", type)) {
  2586. GtkCellRenderer *renderer = NULL;
  2587. GtkTreeModel *model2 = GTK_TREE_MODEL(
  2588. create_model_part(SORTID_PART_STATE));
  2589. if (!model2) {
  2590. g_print("In change part, no model set up for %d(%s)\n",
  2591. SORTID_PART_STATE, partid);
  2592. return;
  2593. }
  2594. entry = gtk_combo_box_new_with_model(model2);
  2595. g_object_unref(model2);
  2596. _set_active_combo_part(GTK_COMBO_BOX(entry),
  2597. model, iter, SORTID_PART_STATE);
  2598. g_signal_connect(entry, "changed",
  2599. G_CALLBACK(_admin_edit_combo_box_part),
  2600. part_msg);
  2601. renderer = gtk_cell_renderer_text_new();
  2602. gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(entry),
  2603. renderer, TRUE);
  2604. gtk_cell_layout_add_attribute(GTK_CELL_LAYOUT(entry),
  2605. renderer, "text", 0);
  2606. label = gtk_dialog_add_button(GTK_DIALOG(popup),
  2607. GTK_STOCK_YES, GTK_RESPONSE_OK);
  2608. gtk_window_set_default(GTK_WINDOW(popup), label);
  2609. gtk_dialog_add_button(GTK_DIALOG(popup),
  2610. GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
  2611. snprintf(tmp_char, sizeof(tmp_char),
  2612. "Which state would you like to set partition '%s' to?",
  2613. partid);
  2614. label = gtk_label_new(tmp_char);
  2615. edit_type = EDIT_PART_STATE;
  2616. } else if (!strcasecmp("Remove Partition", type)) {
  2617. label = gtk_dialog_add_button(GTK_DIALOG(popup),
  2618. GTK_STOCK_YES, GTK_RESPONSE_OK);
  2619. gtk_window_set_default(GTK_WINDOW(popup), label);
  2620. gtk_dialog_add_button(GTK_DIALOG(popup),
  2621. GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
  2622. snprintf(tmp_char, sizeof(tmp_char),
  2623. "Are you sure you want to remove partition %s?",
  2624. partid);
  2625. label = gtk_label_new(tmp_char);
  2626. edit_type = EDIT_REMOVE_PART;
  2627. } else if (!strcasecmp("Edit Partition", type)) {
  2628. label = gtk_dialog_add_button(GTK_DIALOG(popup),
  2629. GTK_STOCK_OK, GTK_RESPONSE_OK);
  2630. gtk_window_set_default(GTK_WINDOW(popup), label);
  2631. gtk_dialog_add_button(GTK_DIALOG(popup),
  2632. GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
  2633. gtk_window_set_default_size(GTK_WINDOW(popup), 200, 400);
  2634. snprintf(tmp_char, sizeof(tmp_char),
  2635. "Editing partition %s think before you type",
  2636. partid);
  2637. label = gtk_label_new(tmp_char);
  2638. edit_type = EDIT_EDIT;
  2639. entry = _admin_full_edit_part(part_msg, model, iter);
  2640. } else if (!strncasecmp("Update", type, 6)) {
  2641. char *old_features = NULL;
  2642. if (got_features_edit_signal)
  2643. old_features = got_features_edit_signal;
  2644. else
  2645. gtk_tree_model_get(model, iter, SORTID_FEATURES,
  2646. &old_features, -1);
  2647. update_features_node(GTK_DIALOG(popup),
  2648. nodelist, old_features);
  2649. if (got_features_edit_signal) {
  2650. got_features_edit_signal = NULL;
  2651. xfree(old_features);
  2652. } else
  2653. g_free(old_features);
  2654. goto end_it;
  2655. } else {
  2656. /* something that has to deal with a node state change */
  2657. update_state_node(GTK_DIALOG(popup), nodelist, type);
  2658. goto end_it;
  2659. }
  2660. gtk_box_pack_start(GTK_BOX(GTK_DIALOG(popup)->vbox),
  2661. label, FALSE, FALSE, 0);
  2662. if (entry)
  2663. gtk_box_pack_start(GTK_BOX(GTK_DIALOG(popup)->vbox),
  2664. entry, TRUE, TRUE, 0);
  2665. gtk_widget_show_all(popup);
  2666. response = gtk_dialog_run (GTK_DIALOG(popup));
  2667. if (response == GTK_RESPONSE_OK) {
  2668. int rc;
  2669. if (global_edit_error)
  2670. temp = global_edit_error_msg;
  2671. else if (edit_type == EDIT_REMOVE_PART) {
  2672. delete_part_msg_t part_del_msg;
  2673. part_del_msg.name = partid;
  2674. rc = slurm_delete_partition(&part_del_msg);
  2675. if (rc == SLURM_SUCCESS) {
  2676. temp = g_strdup_printf(
  2677. "Partition %s removed successfully",
  2678. partid);
  2679. } else {
  2680. temp = g_strdup_printf(
  2681. "Problem removing partition %s: %s",
  2682. partid, slurm_strerror(rc));
  2683. global_multi_error = TRUE;
  2684. }
  2685. } else if (!global_send_update_msg) {
  2686. temp = g_strdup_printf("No change detected.");
  2687. } else if ((rc = slurm_update_partition(part_msg))
  2688. == SLURM_SUCCESS) {
  2689. temp = g_strdup_printf(
  2690. "Partition %s updated successfully",
  2691. partid);
  2692. } else {
  2693. temp = g_strdup_printf(
  2694. "Problem updating partition %s: %s",
  2695. partid, slurm_strerror(rc));
  2696. global_multi_error = TRUE;
  2697. }
  2698. display_edit_note(temp);
  2699. g_free(temp);
  2700. }
  2701. end_it:
  2702. g_free(partid);
  2703. g_free(nodelist);
  2704. global_entry_changed = 0;
  2705. slurm_free_update_part_msg(part_msg);
  2706. gtk_widget_destroy(popup);
  2707. if (got_edit_signal) {
  2708. type = got_edit_signal;
  2709. got_edit_signal = NULL;
  2710. admin_part(model, iter, type);
  2711. xfree(type);
  2712. }
  2713. if (got_features_edit_signal) {
  2714. type = "Update Features";
  2715. admin_part(model, iter, type);
  2716. }
  2717. return;
  2718. }
  2719. extern void cluster_change_part(void)
  2720. {
  2721. display_data_t *display_data = display_data_part;
  2722. while (display_data++) {
  2723. if (display_data->id == -1)
  2724. break;
  2725. if (cluster_flags & CLUSTER_FLAG_BG) {
  2726. switch(display_data->id) {
  2727. case SORTID_NODELIST:
  2728. display_data->name = "MidplaneList";
  2729. break;
  2730. default:
  2731. break;
  2732. }
  2733. } else {
  2734. switch(display_data->id) {
  2735. case SORTID_NODELIST:
  2736. display_data->name = "NodeList";
  2737. break;
  2738. default:
  2739. break;
  2740. }
  2741. }
  2742. }
  2743. display_data = options_data_part;
  2744. while (display_data++) {
  2745. if (display_data->id == -1)
  2746. break;
  2747. if (cluster_flags & CLUSTER_FLAG_BG) {
  2748. switch(display_data->id) {
  2749. case BLOCK_PAGE:
  2750. display_data->name = "Blocks";
  2751. break;
  2752. case NODE_PAGE:
  2753. display_data->name = "Midplanes";
  2754. break;
  2755. }
  2756. if (!display_data->name) {
  2757. } else if (!strcmp(display_data->name, "Drain Nodes"))
  2758. display_data->name = "Drain Midplanes";
  2759. else if (!strcmp(display_data->name, "Resume Nodes"))
  2760. display_data->name = "Resume Midplanes";
  2761. else if (!strcmp(display_data->name, "Put Nodes Down"))
  2762. display_data->name = "Put Midplanes Down";
  2763. else if (!strcmp(display_data->name, "Make Nodes Idle"))
  2764. display_data->name =
  2765. "Make Midplanes Idle";
  2766. else if (!strcmp(display_data->name,
  2767. "Update Node Features"))
  2768. display_data->name =
  2769. "Update Midplanes Features";
  2770. } else {
  2771. switch(display_data->id) {
  2772. case BLOCK_PAGE:
  2773. display_data->name = NULL;
  2774. break;
  2775. case NODE_PAGE:
  2776. display_data->name = "Nodes";
  2777. break;
  2778. }
  2779. if (!display_data->name) {
  2780. } else if (!strcmp(display_data->name,
  2781. "Drain Midplanes"))
  2782. display_data->name = "Drain Nodes";
  2783. else if (!strcmp(display_data->name,
  2784. "Resume Midplanes"))
  2785. display_data->name = "Resume Nodes";
  2786. else if (!strcmp(display_data->name,
  2787. "Put Midplanes Down"))
  2788. display_data->name = "Put Nodes Down";
  2789. else if (!strcmp(display_data->name,
  2790. "Make Midplanes Idle"))
  2791. display_data->name = "Make Nodes Idle";
  2792. else if (!strcmp(display_data->name,
  2793. "Update Node Features"))
  2794. display_data->name =
  2795. "Update Midplanes Features";
  2796. }
  2797. }
  2798. get_info_part(NULL, NULL);
  2799. }