Subversion Repositories ALCASAR

Rev

Details | Last modification | View Log

Rev Author Line No. Line
2782 rexy 1
<?php
2
/**
3
 * Raid Plugin, which displays RAID status
4
 *
5
 * @category  PHP
6
 * @package   PSI_Plugin_Raid
7
 * @author    Mieczyslaw Nalewaj <namiltd@users.sourceforge.net>
8
 * @copyright 2009 phpSysInfo
9
 * @license   http://opensource.org/licenses/gpl-2.0.php GNU General Public License version 2, or (at your option) any later version
10
 * @version   Release: 3.0
11
 * @link      http://phpsysinfo.sourceforge.net
12
 */
13
class Raid extends PSI_Plugin
14
{
15
    /**
16
     * variable, which holds the content of the command
17
     * @var array
18
     */
19
    private $_filecontent = array();
20
 
21
    /**
22
     * variable, which holds the result before the xml is generated out of this array
23
     * @var array
24
     */
25
    private $_result = array();
26
 
27
    private $prog_items = array('mdstat','dmraid','megactl','megasasctl','graid','zpool','idrac');
28
 
29
    /**
30
     * read the data into an internal array and also call the parent constructor
31
     *
32
     * @param String $enc encoding
33
     */
34
    public function __construct($enc)
35
    {
36
        parent::__construct(__CLASS__, $enc);
37
 
38
        $RaidProgs = array();
39
        if (defined('PSI_PLUGIN_RAID_PROGRAM') && is_string(PSI_PLUGIN_RAID_PROGRAM)) {
40
            if (is_string(PSI_PLUGIN_RAID_PROGRAM)) {
41
                if (preg_match(ARRAY_EXP, PSI_PLUGIN_RAID_PROGRAM)) {
42
                    $RaidProgs = eval(strtolower(PSI_PLUGIN_RAID_PROGRAM));
43
                } else {
44
                    $RaidProgs = array(strtolower(PSI_PLUGIN_RAID_PROGRAM));
45
                }
46
            } else {
47
                $this->global_error->addConfigError("__construct()", "[raid] PROGRAM");
48
                exit;
49
            }
50
        } else {
51
            $RaidProgs = $this->prog_items;
52
        }
53
 
54
        $notwas = true;
55
        switch (strtolower(PSI_PLUGIN_RAID_ACCESS)) {
56
        case 'command':
57
        case 'php-snmp':
58
            if ((PSI_OS == 'Linux') && in_array('mdstat', $RaidProgs)) {
59
                CommonFunctions::rfts("/proc/mdstat", $this->_filecontent['mdstat'], 0, 4096, PSI_DEBUG);
60
                $notwas = false;
61
            }
62
            if ((PSI_OS == 'Linux') && in_array('dmraid', $RaidProgs)) {
63
                CommonFunctions::executeProgram("dmraid", "-s -vv 2>&1", $this->_filecontent['dmraid'], PSI_DEBUG);
64
                $notwas = false;
65
            }
66
            if ((PSI_OS == 'Linux') && in_array('megactl', $RaidProgs)) {
67
                CommonFunctions::executeProgram("megactl", "", $this->_filecontent['megactl'], PSI_DEBUG);
68
                $notwas = false;
69
            }
70
            if ((PSI_OS == 'Linux') && in_array('megasasctl', $RaidProgs)) {
71
                CommonFunctions::executeProgram("megasasctl", "", $this->_filecontent['megasasctl'], PSI_DEBUG);
72
                $notwas = false;
73
            }
74
            if ((PSI_OS == 'FreeBSD') && in_array('graid', $RaidProgs)) {
75
                CommonFunctions::executeProgram("graid", "list", $this->_filecontent['graid'], PSI_DEBUG);
76
                $notwas = false;
77
            }
78
            if (in_array('zpool', $RaidProgs)) {
79
                CommonFunctions::executeProgram("zpool", "status", $this->_filecontent['zpool'], PSI_DEBUG);
80
                $notwas = false;
81
            }
82
            if (in_array('idrac', $RaidProgs)) {
83
                if (defined('PSI_PLUGIN_RAID_IDRAC_DEVICES') && is_string(PSI_PLUGIN_RAID_IDRAC_DEVICES)) {
84
                    if (preg_match(ARRAY_EXP, PSI_PLUGIN_RAID_IDRAC_DEVICES)) {
85
                        $devices = eval(PSI_PLUGIN_RAID_IDRAC_DEVICES);
86
                    } else {
87
                        $devices = array(PSI_PLUGIN_RAID_IDRAC_DEVICES);
88
                    }
89
                    if (strtolower(PSI_PLUGIN_RAID_ACCESS)=="command") {
90
                        foreach ($devices as $device) {
91
                            CommonFunctions::executeProgram("snmpwalk", "-Ona -c public -v 1 -t ".PSI_SNMP_TIMEOUT_INT." -r ".PSI_SNMP_RETRY_INT." ".$device." .1.3.6.1.4.1.674.10892.5.5.1.20", $buffer, PSI_DEBUG);
92
                            if (strlen($buffer) > 0) {
93
                                $this->_filecontent['idrac'][$device] = $buffer;
94
                            }
95
                        }
96
                    } else {
97
                        snmp_set_valueretrieval(SNMP_VALUE_LIBRARY);
98
                        snmp_set_oid_output_format(SNMP_OID_OUTPUT_NUMERIC);
99
                        foreach ($devices as $device) {
100
                            if (! PSI_DEBUG) {
101
                                restore_error_handler(); /* default error handler */
102
                                $old_err_rep = error_reporting();
103
                                error_reporting(E_ERROR); /* fatal errors only */
104
                            }
105
                            $bufferarr=snmprealwalk($device, "public", ".1.3.6.1.4.1.674.10892.5.5.1.20", 1000000 * PSI_SNMP_TIMEOUT_INT, PSI_SNMP_RETRY_INT);
106
                            if (! PSI_DEBUG) {
107
                                error_reporting($old_err_rep); /* restore error level */
108
                                set_error_handler('errorHandlerPsi'); /* restore error handler */
109
                            }
110
                            if (! empty($bufferarr)) {
111
                                $buffer="";
112
                                foreach ($bufferarr as $id=>$string) {
113
                                    $buffer .= $id." = ".$string."\n";
114
                                }
115
                                if (strlen($buffer) > 0) {
116
                                    $this->_filecontent['idrac'][$device] = $buffer;
117
                                }
118
                            }
119
                        }
120
                    }
121
                }
122
 
123
                $notwas = false;
124
            }
125
            if ($notwas) {
126
                $this->global_error->addConfigError("__construct()", "[raid] PROGRAM");
127
            }
128
            break;
129
        case 'data':
130
            foreach ($this->prog_items as $item) {
131
                if (in_array($item, $RaidProgs)) {
132
                    if ($item !== 'idrac') {
133
                        CommonFunctions::rfts(PSI_APP_ROOT."/data/raid".$item.".txt", $this->_filecontent[$item], 0, 4096, false);
134
                    } elseif (defined('PSI_PLUGIN_RAID_IDRAC_DEVICES') && is_string(PSI_PLUGIN_RAID_IDRAC_DEVICES)) {
135
                        if (preg_match(ARRAY_EXP, PSI_PLUGIN_RAID_IDRAC_DEVICES)) {
136
                            $devices = eval(PSI_PLUGIN_RAID_IDRAC_DEVICES);
137
                        } else {
138
                            $devices = array(PSI_PLUGIN_RAID_IDRAC_DEVICES);
139
                        }
140
                        $pn=0;
141
                        foreach ($devices as $device) {
142
                            $buffer="";
143
                            if (CommonFunctions::rfts(PSI_APP_ROOT."/data/raid".$item.$pn.".txt", $buffer) && !empty($buffer)) {
144
                                $this->_filecontent['idrac'][$device] = $buffer;
145
                            }
146
                            $pn++;
147
                        }
148
                    }
149
                    $notwas = false;
150
                }
151
            }
152
            if ($notwas) {
153
                $this->global_error->addConfigError("__construct()", "[raid] PROGRAM");
154
            }
155
            break;
156
        default:
157
            $this->global_error->addConfigError("__construct()", "[raid] ACCESS");
158
            break;
159
        }
160
    }
161
 
162
    private function execute_mdstat($buffer)
163
    {
164
        $raiddata = preg_split("/\r?\n/", $buffer, -1, PREG_SPLIT_NO_EMPTY);
165
        if (!empty($raiddata)) {
166
            // get the supported types
167
            $supported = '';
168
            if (preg_match('/^[a-zA-Z]+ :( \[[a-z0-9]+\])+/', $raiddata[0], $res)) {
169
                $parts = preg_split("/ : /", $res[0]);
170
                if (isset($parts[1]) && (trim($parts[1]) !== '')) {
171
                    $supported = preg_replace('/[\[\]]/', '', trim($parts[1]));
172
                }
173
            }
174
            // get disks
175
            if (preg_match("/^read_ahead/", $raiddata[1])) {
176
                $count = 2;
177
            } else {
178
                $count = 1;
179
            }
180
            $cnt_filecontent = count($raiddata);
181
            do {
182
                $parts = preg_split("/ : /", $raiddata[$count]);
183
                $dev = trim($parts[0]);
184
                if (count($parts) == 2) {
185
                    $this->_result['devices'][$dev]['prog'] = "mdstat";
186
                    if ($supported !== '') $this->_result['devices'][$dev]['supported'] = $supported;
187
                    $this->_result['devices'][$dev]['items'][0]['raid_index'] = -1; //must by first
188
                    $details = preg_split('/ /', $parts[1]);
189
                    if (!strstr($details[0], 'inactive')) {
190
                        if (isset($details[2]) && strstr($details[1], '(auto-read-only)')) {
191
                            $this->_result['devices'][$dev]['level'] = $details[2];
192
                            $this->_result['devices'][$dev]['status'] = $details[0]." ".$details[1];
193
                            //$this->_result['devices'][$dev]['items'][0]['name'] = $dev." ".$details[2];
194
                            $this->_result['devices'][$dev]['items'][0]['name'] = $details[2];
195
                            $this->_result['devices'][$dev]['items'][0]['status'] = "W";
196
                            $i = 3;
197
                        } else {
198
                            $this->_result['devices'][$dev]['level'] = $details[1];
199
                            $this->_result['devices'][$dev]['status'] = $details[0];
200
                            //$this->_result['devices'][$dev]['items'][0]['name'] = $dev." ".$details[1];
201
                            $this->_result['devices'][$dev]['items'][0]['name'] = $details[1];
202
                            $this->_result['devices'][$dev]['items'][0]['status'] = "ok";
203
                            $i = 2;
204
                        }
205
                    } else {
206
                        $this->_result['devices'][$dev]['level'] = "none";
207
                        $this->_result['devices'][$dev]['status'] = $details[0];
208
                        $this->_result['devices'][$dev]['items'][0]['name'] = $dev;
209
                        $this->_result['devices'][$dev]['items'][0]['status'] = "F";
210
                        $i = 1;
211
                    }
212
                    $this->_result['devices'][$dev]['items'][0]['parentid'] = 0;
213
 
214
                    for ($cnt_details = count($details); $i < $cnt_details; $i++) {
215
                        preg_match('/(([a-z0-9])+)(\[([0-9]+)\])(\([SF ]\))?/', trim($details[$i]), $partition);
216
                        if (count($partition) == 5 || count($partition) == 6) {
217
                            $this->_result['devices'][$dev]['items'][$partition[1]]['raid_index'] = 0+substr(trim($partition[3]), 1, -1);
218
                            if (isset($partition[5])) {
219
                                $search = array("(", ")");
220
                                $replace = array("", "");
221
                                $this->_result['devices'][$dev]['items'][$partition[1]]['status'] = str_replace($search, $replace, trim($partition[5]));
222
                            } else {
223
                                $this->_result['devices'][$dev]['items'][$partition[1]]['status'] = "ok";
224
                            }
225
                            $this->_result['devices'][$dev]['items'][$partition[1]]['name'] = $partition[1];
226
                            $this->_result['devices'][$dev]['items'][$partition[1]]['parentid'] = 1;
227
                            $this->_result['devices'][$dev]['items'][$partition[1]]['type'] = "disk";
228
                        }
229
                    }
230
                    $optionline = $raiddata[$count].$raiddata[$count+1];
231
                    $count++;
232
                    if (preg_match('/([^\sk]*)k chunk/', $optionline, $chunksize)) {
233
                        $this->_result['devices'][$dev]['chunk_size'] = $chunksize[1];
234
                    }
235
                    if ($pos = strpos($optionline, "super non-persistent")) {
236
                        $this->_result['devices'][$dev]['pers_superblock'] = 0;
237
                    } else {
238
                        $this->_result['devices'][$dev]['pers_superblock'] = 1;
239
                    }
240
                    if ($pos = strpos($optionline, "algorithm")) {
241
                        $this->_result['devices'][$dev]['algorithm'] = trim(substr($optionline, $pos + 9, 2));
242
                    }
243
                    if (preg_match('/\[([0-9]+)\/([0-9]+)\]/', $optionline, $res)) {
244
                        $this->_result['devices'][$dev]['registered'] = $res[1];
245
                        $this->_result['devices'][$dev]['active'] = $res[2];
246
                    }
247
 
248
                    if (isset($this->_result['devices'][$dev]['items'])) {
249
                        asort($this->_result['devices'][$dev]['items']);
250
                    }
251
                    if ((!isset($this->_result['devices'][$dev]['registered']) || ($this->_result['devices'][$dev]['registered']<24)) && preg_match('/\[([_U]+)\]/', $optionline, $res) && (($reslen=strlen($res[1])) > 0)) {
252
                        $notsparecount = 0;
253
                        foreach ($this->_result['devices'][$dev]['items'] as $diskkey=>$disk) {
254
                            if (($diskkey!==0) && ($this->_result['devices'][$dev]['items'][$diskkey]['status']!=="S")) {
255
                                $notsparecount++;
256
                            }
257
                        }
258
                        if ($notsparecount == $reslen) {
259
                            $partnr = 0;
260
                            foreach ($this->_result['devices'][$dev]['items'] as $diskkey=>$disk) {
261
                                if (($diskkey!==0) && ($this->_result['devices'][$dev]['items'][$diskkey]['status']!=="S")) {
262
                                    if (($res[1][$partnr]=='_') && ($this->_result['devices'][$dev]['items'][$diskkey]['status']=="ok")) {
263
                                        $this->_result['devices'][$dev]['items'][$diskkey]['status']="W";
264
                                    }
265
                                    $partnr++;
266
                                }
267
                            }
268
                        } elseif ($reslen-$notsparecount == 1) {
269
                            $partnr = 0;
270
                            foreach ($this->_result['devices'][$dev]['items'] as $diskkey=>$disk) {
271
                                if (($diskkey!==0) && ($this->_result['devices'][$dev]['items'][$diskkey]['status']!=="S")) {
272
                                    if ($res[1][$partnr]=='_') {
273
                                        $this->_result['devices'][$dev]['items']['none']['raid_index']=$this->_result['devices'][$dev]['items'][$diskkey]['raid_index']-1;
274
                                        $this->_result['devices'][$dev]['items']['none']['status']="E";
275
                                        $this->_result['devices'][$dev]['items']['none']['name']="none";
276
                                        $this->_result['devices'][$dev]['items']['none']['parentid'] = 1;
277
                                        $this->_result['devices'][$dev]['items']['none']['type'] = "disk";
278
                                    }
279
                                    $partnr++;
280
                                }
281
                            }
282
                            if ($res[1][$partnr]=='_') {
283
                                $this->_result['devices'][$dev]['items']['none']['raid_index']=$this->_result['devices'][$dev]['items'][$diskkey]['raid_index']+1;
284
                                $this->_result['devices'][$dev]['items']['none']['status']="E";
285
                                $this->_result['devices'][$dev]['items']['none']['name']="none";
286
                                $this->_result['devices'][$dev]['items']['none']['parentid'] = 1;
287
                                $this->_result['devices'][$dev]['items']['none']['type']="disk";
288
                            }
289
                            asort($this->_result['devices'][$dev]['items']);
290
                            foreach ($this->_result['devices'][$dev]['items'] as $diskkey=>$disk) {
291
                                if ($diskkey=="none") {
292
                                    $this->_result['devices'][$dev]['items'][$diskkey]['raid_index']="unknown";
293
                                }
294
                            }
295
                        } else {
296
                            foreach ($this->_result['devices'][$dev]['items'] as $diskkey=>$disk) {
297
                                if ($this->_result['devices'][$dev]['items'][$diskkey]['status']=="ok") {
298
                                    $this->_result['devices'][$dev]['items'][$diskkey]['status']="W";
299
                                }
300
                            }
301
                            for ($partnr=0; $partnr<$reslen-$notsparecount; $partnr++) {
302
                                    $this->_result['devices'][$dev]['items']['none'.$partnr]['raid_index']="unknown";
303
                                    $this->_result['devices'][$dev]['items']['none'.$partnr]['status']="E";
304
                                    $this->_result['devices'][$dev]['items']['none'.$partnr]['name'] = "none".$partnr;
305
                                    $this->_result['devices'][$dev]['items']['none'.$partnr]['parentid'] = 1;
306
                                    $this->_result['devices'][$dev]['items']['none'.$partnr]['type'] = "disk";
307
                            }
308
                        }
309
                    }
310
                    if (preg_match(('/([a-z]+)( *)=( *)([0-9\.]+)%/'), $raiddata[$count + 1], $res) || (preg_match(('/([a-z]+)( *)=( *)([0-9\.]+)/'), $optionline, $res))) {
311
                        list($this->_result['devices'][$dev]['action']['name'], $this->_result['devices'][$dev]['action']['percent']) = preg_split("/=/", str_replace("%", "", $res[0]));
312
                        if (preg_match(('/([a-z]*=[0-9\.]+[a-z]+)/'), $raiddata[$count + 1], $res)) {
313
                            $time = preg_split("/=/", $res[0]);
314
                            list($this->_result['devices'][$dev]['action']['finish_time'], $this->_result['devices'][$dev]['action']['finish_unit']) = sscanf($time[1], '%f%s');
315
                        }
316
                    } elseif (preg_match(('/^( *)([a-z]+)( *)=( *)([A-Z]+)$/'), $raiddata[$count + 1], $res)) {
317
                       $this->_result['devices'][$dev]['status'] .= " ".trim($raiddata[$count + 1]);
318
                    }
319
                } else {
320
                    $count++;
321
                }
322
            } while ($cnt_filecontent > $count);
323
            $lastline = $raiddata[$cnt_filecontent - 1];
324
            if (strpos($lastline, "unused devices") !== false) {
325
                $parts = preg_split("/:/", $lastline);
326
                $unused = trim($parts[1]);
327
                if ($unused !== "<none>") {
328
                    $details = preg_split('/ /', $parts[1], -1, PREG_SPLIT_NO_EMPTY);
329
                    $this->_result['devices']['spare']['prog'] = "mdstat";
330
                    $this->_result['devices']['spare']['status'] = "spare";
331
                    $this->_result['devices']['spare']['items'][0]['name'] = "spare";
332
                    $this->_result['devices']['spare']['items'][0]['parentid'] = 0;
333
                    $this->_result['devices']['spare']['items'][0]['status'] = "S";
334
                    foreach ($details as $id=>$disk) {
335
                        $this->_result['devices']['spare']['items'][$id+1]['name'] = $disk;
336
                        $this->_result['devices']['spare']['items'][$id+1]['parentid'] = 1;
337
                        $this->_result['devices']['spare']['items'][$id+1]['status'] = "S";
338
                        $this->_result['devices']['spare']['items'][$id+1]['type'] = "disk";
339
                    }
340
                }
341
            }
342
        }
343
    }
344
 
345
    private function execute_dmraid($buffer)
346
    {
347
        $raiddata = preg_split("/(\r?\n\*\*\* )|(\r?\n--> )/", $buffer, -1, PREG_SPLIT_NO_EMPTY);
348
        if (!empty($raiddata)) {
349
            $group = "";
350
            foreach ($raiddata as $block) {
351
                if (preg_match('/^(NOTICE: )|(ERROR: )/m', $block)) {
352
                    $group = "";
353
                    $lines = preg_split("/\r?\n/", $block, -1, PREG_SPLIT_NO_EMPTY);
354
                    foreach ($lines as $line) {
355
                        if (preg_match('/^NOTICE: added\s+\/dev\/(.+)\s+to RAID set\s+\"(.+)\"/', $line, $partition)) {
356
                            if (!isset($this->_result['devices'][$partition[2]]['items'][0]['parentid'])) {
357
                                $this->_result['devices'][$partition[2]]['items'][0]['parentid'] = 0;
358
                                $this->_result['devices'][$partition[2]]['items'][0]['name'] = $partition[2];
359
                            }
360
                            $this->_result['devices'][$partition[2]]['items'][$partition[1]]['status'] = "ok";
361
                            $this->_result['devices'][$partition[2]]['items'][$partition[1]]['type'] = "disk";
362
                            $this->_result['devices'][$partition[2]]['items'][$partition[1]]['parentid'] = 1;
363
                            $this->_result['devices'][$partition[2]]['items'][$partition[1]]['name'] = $partition[1];
364
                            $this->_result['devices'][$partition[2]]['prog'] = "dmraid";
365
                            $this->_result['devices'][$partition[2]]['status'] = "ok";
366
                            $this->_result['devices'][$partition[2]]['level'] = "unknown";
367
                        } elseif (preg_match('/^ERROR: .* device\s+\/dev\/(.+)\s+(.+)\s+in RAID set\s+\"(.+)\"/', $line, $partition)) {
368
                            if (!isset($this->_result['devices'][$partition[3]]['items'][0]['parentid'])) {
369
                                $this->_result['devices'][$partition[3]]['items'][0]['parentid'] = 0;
370
                                $this->_result['devices'][$partition[3]]['items'][0]['name'] = $partition[3];
371
                            }
372
                            $this->_result['devices'][$partition[3]]['prog'] = "dmraid";
373
                            $this->_result['devices'][$partition[3]]['level'] = "unknown";
374
                            $this->_result['devices'][$partition[3]]['items'][$partition[1]]['type'] = "disk";
375
                            $this->_result['devices'][$partition[3]]['items'][$partition[1]]['parentid'] = 1;
376
                            if ($partition[2]=="broken") {
377
                                $this->_result['devices'][$partition[3]]['items'][$partition[1]]['status'] = "F";
378
                                $this->_result['devices'][$partition[3]]['status'] = "F";
379
                            } else {
380
                                $this->_result['devices'][$partition[3]]['items'][$partition[1]]['status'] = "W";
381
                                $this->_result['devices'][$partition[3]]['status'] = "W";
382
                            }
383
                            $this->_result['devices'][$partition[3]]['items'][$partition[1]]['name'] = $partition[1];
384
                        }
385
                    }
386
                } else {
387
                    if (preg_match('/^Group superset\s+(.+)/m', $block, $arrname)) {
388
                        $group = trim($arrname[1]);
389
                    }
390
                    if (preg_match('/^name\s*:\s*(.*)/m', $block, $arrname)) {
391
                        if ($group=="") {
392
                            $group = trim($arrname[1]);
393
                        }
394
                        $this->_result['devices'][$group]['prog'] = "dmraid";
395
                        $this->_result['devices'][$group]['name'] = trim($arrname[1]);
396
 
397
                        $this->_result['devices'][$group]['items'][0]['name'] = trim($arrname[1]);
398
 
399
                        if (preg_match('/^size\s*:\s*(.*)/m', $block, $size)) {
400
                            $this->_result['devices'][$group]['size'] = trim($size[1]);
401
                        }
402
                        if (preg_match('/^stride\s*:\s*(.*)/m', $block, $stride)) {
403
                                $this->_result['devices'][$group]['stride'] = trim($stride[1]);
404
                        }
405
                        if (preg_match('/^type\s*:\s*(.*)/m', $block, $type)) {
406
                            $this->_result['devices'][$group]['level'] = trim($type[1]);
407
                            //$this->_result['devices'][$group]['items'][0]['name'] .= " ".trim($type[1]);
408
                            $this->_result['devices'][$group]['items'][0]['name'] = trim($type[1]);
409
                        }
410
                        if (preg_match('/^status\s*:\s*(.*)/m', $block, $status)) {
411
                            $this->_result['devices'][$group]['status'] = trim($status[1]);
412
                            switch (trim($status[1])) {
413
                                case "broken":
414
                                    $this->_result['devices'][$group]['items'][0]['status'] = "F";
415
                                    break;
416
                                case "inconsistent":
417
                                    $this->_result['devices'][$group]['items'][0]['status'] = "W";
418
                                    break;
419
                                default:
420
                                    $this->_result['devices'][$group]['items'][0]['status'] = trim($status[1]);
421
                            }
422
                        }
423
                        if (preg_match('/^subsets\s*:\s*(.*)/m', $block, $subsets)) {
424
                            $this->_result['devices'][$group]['subsets'] = trim($subsets[1]);
425
                        }
426
                        if (preg_match('/^devs\s*:\s*(.*)/m', $block, $devs)) {
427
                            $this->_result['devices'][$group]['devs'] = trim($devs[1]);
428
                        }
429
                        if (preg_match('/^spares\s*:\s*(.*)/m', $block, $spares)) {
430
                                $this->_result['devices'][$group]['spares'] = trim($spares[1]);
431
                        }
432
 
433
                        if (!isset($this->_result['devices'][$group]['items'][0]['parentid'])) {
434
                            $this->_result['devices'][$group]['items'][0]['parentid'] = 0;
435
                        }
436
 
437
                        $group = "";
438
                    }
439
                }
440
            }
441
            if (isset($this->_result['devices'])) {
442
                foreach ($this->_result['devices'] as $gid=>$group) if ($group['prog'] === "dmraid") {
443
                    $id = 1;
444
                    if (isset($group['devs']) && ($group['devs']>0) &&
445
                       (!isset($group['items']) || (count($group['items'])<$group['devs'])) &&
446
                       isset($group['subsets']) && ($group['subsets']>0)) for ($i = 0; $i < $group['subsets']; $i++) {
447
                        if (isset($this->_result['devices'][$gid."-".$i]['items'][0]['parentid'])) {
448
                            foreach ($this->_result['devices'][$gid."-".$i]['items'] as $fid=>$from) {
449
                                if ($fid===0) {
450
                                    $this->_result['devices'][$gid]['items'][$gid."-".$i]['parentid'] = 1;
451
                                    $this->_result['devices'][$gid]['items'][$gid."-".$i]['status'] = $from['status'];
452
                                    $this->_result['devices'][$gid]['items'][$gid."-".$i]['name'] = $gid."-".$i." ".$from['name'];
453
                                    if (isset($from['type'])) $this->_result['devices'][$gid]['items'][$gid."-".$i]['type'] = $from['type'];
454
                                } else {
455
                                    $this->_result['devices'][$gid]['items'][$from['name']]['parentid'] = 1+$id;
456
                                    $this->_result['devices'][$gid]['items'][$from['name']]['status'] = $from['status'];
457
                                    $this->_result['devices'][$gid]['items'][$from['name']]['name'] = $from['name'];
458
                                    if (isset($from['type'])) $this->_result['devices'][$gid]['items'][$from['name']]['type'] = $from['type'];
459
                                }
460
                            }
461
                            $id+=count($this->_result['devices'][$gid."-".$i]['items']);
462
                            unset($this->_result['devices'][$gid."-".$i]);
463
                        } else {
464
                            $this->_result['devices'][$gid]['items'][$gid."-".$i]['parentid'] = 1;
465
                            $this->_result['devices'][$gid]['items'][$gid."-".$i]['status'] = "unknown";
466
                            $this->_result['devices'][$gid]['items'][$gid."-".$i]['name'] = $gid."-".$i;
467
                            $id++;
468
                        }
469
                    }
470
                }
471
                foreach ($this->_result['devices'] as $gid=>$group) if ($group['prog'] === "dmraid") {
472
                    if (($group['name'] !== $gid) && isset($group['items'][0]['parentid'])) {
473
                        $this->_result['devices'][$gid]['items'][0]['name'] = $group['name']." ".$group['items'][0]['name'];
474
                    }
475
                }
476
            }
477
        }
478
    }
479
 
480
    private function execute_megactl($buffer, $sas = false)
481
    {
482
        $raiddata = preg_split("/(\r?\n)+(?=[a-z]\d+ )/", $buffer, -1, PREG_SPLIT_NO_EMPTY);
483
        if (!empty($raiddata)) foreach ($raiddata as $raidgroup) {
484
            if (preg_match("/^([a-z]\d+) /", $raidgroup, $buff)) {
485
                if (preg_match("/^[a-z]\d+ ([^:\r\n]+) [^:\r\n]+:/", $raidgroup, $geom) || preg_match("/^[a-z]\d+ ([^:\r\n]+)/", $raidgroup, $geom)) {
486
                    $controller = trim($geom[1]);
487
                } else {
488
                    $controller = '';
489
                }
490
                if (preg_match("/^[a-z]\d+ [^:\r\n]+ [^\r\n]* batt:([^:\r\n,]+)/", $raidgroup, $batt)) {
491
                    $battery = trim($batt[1]);
492
                } else {
493
                    $battery = '';
494
                }
495
                $group = $buff[1];
496
                $lines = preg_split("/\r?\n/", $raidgroup, -1, PREG_SPLIT_NO_EMPTY);
497
                if (!empty($lines)) {
498
                    if ($sas === true) {
499
                        $prog = "megasasctl";
500
                        $prefix = "/"; //for megactl and megasasctl conflicts
501
                    } else {
502
                        $prog = "megactl";
503
                        $prefix = "";
504
                    }
505
                    unset($lines[0]);
506
                    foreach ($lines as $line) {
507
                        $details = preg_split('/ /', preg_replace('/^hot spares +:/', 'hotspare:', $line), -1, PREG_SPLIT_NO_EMPTY);
508
                        if ((count($details) == 6) && ($details[2] === "RAID")) {
509
                            $this->_result['devices'][$prefix.$details[0]]['prog'] = $prog;
510
                            $unit = preg_replace("/^\d+/", "", $details[1]);
511
                            $value = preg_replace("/\D+$/", "", $details[1]);
512
                            switch ($unit) {
513
                                case 'B':
514
                                    $this->_result['devices'][$prefix.$details[0]]['size'] = $value;
515
                                    break;
516
                                case 'KiB':
517
                                    $this->_result['devices'][$prefix.$details[0]]['size'] = 1024*$value;
518
                                    break;
519
                                case 'MiB':
520
                                    $this->_result['devices'][$prefix.$details[0]]['size'] = 1024*1024*$value;
521
                                    break;
522
                                case 'GiB':
523
                                    $this->_result['devices'][$prefix.$details[0]]['size'] = 1024*1024*1024*$value;
524
                                    break;
525
                                case 'TiB':
526
                                    $this->_result['devices'][$prefix.$details[0]]['size'] = 1024*1024*1024*1024*$value;
527
                                    break;
528
                                case 'PiB':
529
                                    $this->_result['devices'][$prefix.$details[0]]['size'] = 1024*1024*1024*1024*1024*$value;
530
                                    break;
531
                            }
532
                            $this->_result['devices'][$prefix.$details[0]]['level'] = "RAID".$details[3]." ".$details[4];
533
                            $this->_result['devices'][$prefix.$details[0]]['status'] = $details[5];
534
                            if ($controller !== '') $this->_result['devices'][$prefix.$details[0]]['controller'] = $controller;
535
                            if ($battery !== '') $this->_result['devices'][$prefix.$details[0]]['battery'] = $battery;
536
                            $this->_result['devices'][$prefix.$details[0]]['items'][$details[0]]['parentid'] = 0;
537
                            $this->_result['devices'][$prefix.$details[0]]['items'][$details[0]]['name'] = "RAID".$details[3]." ".$details[4];
538
                            if ($details[5] !== 'optimal') {
539
                                $this->_result['devices'][$prefix.$details[0]]['items'][$details[0]]['info'] = $details[5];
540
                            }
541
                            switch ($details[5]) {
542
                                case 'optimal':
543
                                    $this->_result['devices'][$prefix.$details[0]]['items'][$details[0]]['status'] = "ok";
544
                                    break;
545
                                case 'OFFLINE':
546
                                    $this->_result['devices'][$prefix.$details[0]]['items'][$details[0]]['status'] = "F";
547
                                    break;
548
                                default:
549
                                    $this->_result['devices'][$prefix.$details[0]]['items'][$details[0]]['status'] = "W";
550
                            }
551
                        } elseif (count($details) == 4) {
552
                            if (isset($this->_result['devices'][$prefix.$details[2]])) {
553
                                $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['parentid'] = 1;
554
                                $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['type'] = 'disk';
555
                                $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['name'] = $details[0];
556
                                if ($details[3] !== 'online') {
557
                                    $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['info'] = $details[3];
558
                                }
559
                                switch ($details[3]) {
560
                                    case 'online':
561
                                        $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['status'] = "ok";
562
                                        break;
563
                                    case 'hotspare':
564
                                        $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['status'] = "S";
565
                                        break;
566
                                    case 'rdy/fail':
567
                                        $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['status'] = "F";
568
                                        break;
569
                                    default:
570
                                        $this->_result['devices'][$prefix.$details[2]]['items'][$details[0]]['status'] = "W";
571
                                }
572
                            }
573
                        } elseif ((count($details) == 2) && (($details[0]==='unconfigured:') || ($details[0]==='hotspare:'))) {
574
                            $itemn0 = rtrim($details[0], ':');
575
                            $itemn = $group .'-'.$itemn0;
576
                            $this->_result['devices'][$prefix.$itemn]['status'] = $itemn0;
577
                            $this->_result['devices'][$prefix.$itemn]['prog'] = $prog;
578
                            if ($controller !== '') $this->_result['devices'][$prefix.$itemn]['controller'] = $controller;
579
                            if ($battery !== '') $this->_result['devices'][$prefix.$itemn]['battery'] = $battery;
580
                            $this->_result['devices'][$prefix.$itemn]['items'][$itemn]['parentid'] = 0;
581
                            $this->_result['devices'][$prefix.$itemn]['items'][$itemn]['name'] = $itemn0;
582
                            if ($details[0]==='unconfigured:') {
583
                                $this->_result['devices'][$prefix.$itemn]['items'][$itemn]['status'] = "U";
584
                            } else {
585
                                $this->_result['devices'][$prefix.$itemn]['items'][$itemn]['status'] = "S";
586
                            }
587
                        } elseif (count($details) == 3) {
588
                            $itemn = '';
589
                            switch ($details[2]) {
590
                                case 'BAD':
591
                                case 'ready':
592
                                    $itemn = $group .'-'.'unconfigured';
593
                                    break;
594
                                case 'hotspare':
595
                                    $itemn = $group .'-'.'hotspare';
596
                            }
597
                            if (($itemn !== '') && isset($this->_result['devices'][$prefix.$itemn])) {
598
                                $this->_result['devices'][$prefix.$itemn]['items'][$details[0]]['parentid'] = 1;
599
                                $this->_result['devices'][$prefix.$itemn]['items'][$details[0]]['type'] = 'disk';
600
                                $this->_result['devices'][$prefix.$itemn]['items'][$details[0]]['name'] = $details[0];
601
                                $this->_result['devices'][$prefix.$itemn]['items'][$details[0]]['info'] = $details[2];
602
                                switch ($details[2]) {
603
                                    case 'ready':
604
                                        $this->_result['devices'][$prefix.$itemn]['items'][$details[0]]['status'] = "U";
605
                                        break;
606
                                    case 'hotspare':
607
                                        $this->_result['devices'][$prefix.$itemn]['items'][$details[0]]['status'] = "S";
608
                                        break;
609
                                    default:
610
                                        $this->_result['devices'][$prefix.$itemn]['items'][$details[0]]['status'] = "F";
611
                                }
612
                            }
613
                        }
614
                    }
615
                }
616
            }
617
        }
618
    }
619
 
620
    private function execute_graid($buffer)
621
    {
622
        if (preg_match('/^Geom name: +([^\n\r]+)/', $buffer, $geom)) {
623
            $controller = trim($geom[1]);
624
        } else {
625
            $controller = '';
626
        }
627
        $raiddata = preg_split("/Consumers:\r?\n/", $buffer, -1, PREG_SPLIT_NO_EMPTY);
628
        if (!empty($raiddata)) {
629
            $disksinfo = array();
630
            if (isset($raiddata[1]) && (trim($raiddata[1])!=="")) {
631
                $lines = preg_split("/\r?\n/", trim($raiddata[1]), -1, PREG_SPLIT_NO_EMPTY);
632
                $disk = "";
633
                foreach ($lines as $line) {
634
                    if (preg_match("/^\d+\.\s+Name:\s+(.+)/", $line, $data)) {
635
                        $disk = $data[1];
636
                    } elseif (($disk!=="") && preg_match('/^\s+State:\s+(\S+)\s+\(([^\)\s]+)\s*([\d]*)(%*)([^\)]*)\)/', $line, $data)) {
637
                        $disksinfo[$disk]['status'] = trim($data[1]);
638
                        $disksinfo[$disk]['substatus'] = trim($data[2]);
639
                        if (trim($data[4])=="%") {
640
                            $disksinfo[$disk]['percent'] = trim($data[3]);
641
                        }
642
                    }
643
                }
644
            }
645
            $lines = preg_split("/\r?\n/", trim($raiddata[0]), -1, PREG_SPLIT_NO_EMPTY);
646
            $group = "";
647
            foreach ($lines as $line) {
648
                if (preg_match("/^\d+\.\s+Name:\s+(.+)/", $line, $data)) {
649
                    $group = $data[1];
650
                    $this->_result['devices'][$group]['prog'] = "graid";
651
                    if ($controller !== '') $this->_result['devices'][$group]['controller'] = $controller;
652
                } elseif ($group!=="") {
653
                    if (preg_match('/^\s+Mediasize:\s+(\d+)/', $line, $data)) {
654
                        $this->_result['devices'][$group]['size'] = trim($data[1]);
655
                    } elseif (preg_match('/^\s+State:\s+(.+)/', $line, $data)) {
656
                        $this->_result['devices'][$group]['status'] = trim($data[1]);
657
                    } elseif (preg_match('/^\s+RAIDLevel:\s+(.+)/', $line, $data)) {
658
                        $this->_result['devices'][$group]['level'] = trim($data[1]);
659
                    } elseif (preg_match('/^\s+Components:\s+(\d+)/', $line, $data)) {
660
                        $this->_result['devices'][$group]['devs'] = trim($data[1]);
661
                    } elseif (preg_match('/^\s+Label:\s+(.+)/', $line, $data)) {
662
                        $this->_result['devices'][$group]['name'] = trim($data[1]);
663
                    } elseif (preg_match('/^\s+Subdisks:\s+(.+)/', $line, $data)) {
664
                        $disks = preg_split('/\s*,\s*/', trim($data[1]), -1, PREG_SPLIT_NO_EMPTY);
665
                        $nones = 0;
666
                        $this->_result['devices'][$group]['items'][0]['parentid'] = 0;
667
                        foreach ($disks as $disk) {
668
                            if (preg_match("/^(\S+)\s+\(([^\)]+)\)/", $disk, $partition)) {
669
                                $this->_result['devices'][$group]['items'][$partition[1]]['parentid'] = 1;
670
                                $this->_result['devices'][$group]['items'][$partition[1]]['type'] = "disk";
671
                                if ($partition[2]=="ACTIVE") {
672
                                    if (isset($disksinfo[$partition[1]]["status"])) {
673
                                        if ($disksinfo[$partition[1]]["status"]!=="ACTIVE") {
674
                                            $this->_result['devices'][$group]['items'][$partition[1]]['status'] = "W";
675
                                        } elseif ($disksinfo[$partition[1]]["substatus"]=="ACTIVE") {
676
                                            $this->_result['devices'][$group]['items'][$partition[1]]['status'] = "ok";
677
                                        } else {
678
                                            $this->_result['devices'][$group]['items'][$partition[1]]['status'] = "W";
679
                                            if (isset($disksinfo[$partition[1]]["percent"])) {
680
                                                $this->_result['devices'][$group]['action']['name'] = $disksinfo[$partition[1]]["substatus"];
681
                                                $this->_result['devices'][$group]['action']['percent'] = $disksinfo[$partition[1]]["percent"];
682
                                            }
683
                                        }
684
                                    } else {
685
                                        $this->_result['devices'][$group]['items'][$partition[1]]['status'] = "ok";
686
                                        $this->_result['devices'][$group]['items'][$partition[1]]['name'] = $partition[1];
687
                                    }
688
                                    $this->_result['devices'][$group]['items'][$partition[1]]['name'] = $partition[1];
689
                                } elseif ($partition[2]=="NONE") {
690
                                    $this->_result['devices'][$group]['items']["none".$nones]['status'] = 'E';
691
                                    $this->_result['devices'][$group]['items']["none".$nones]['name'] = "none".$nones;
692
                                    $nones++;
693
                                }
694
                            }
695
                        }
696
                    }
697
                }
698
            }
699
            if (isset($this->_result['devices'][$group]['items'][0]['parentid'])) {
700
                $name = "";
701
                if (isset($this->_result['devices'][$group]['name'])) {
702
                    $name = $this->_result['devices'][$group]['name'];
703
                }
704
                if (isset($this->_result['devices'][$group]['level'])) {
705
                    $name .= " " .$this->_result['devices'][$group]['level'];
706
                }
707
                $this->_result['devices'][$group]['items'][0]['name'] = trim($name);
708
                if (isset($this->_result['devices'][$group]['status'])) {
709
                      if ($this->_result['devices'][$group]['status']==="OPTIMAL") {
710
                          $this->_result['devices'][$group]['items'][0]['status'] = "ok";
711
                      } else {
712
                          $this->_result['devices'][$group]['items'][0]['status'] = "W";
713
                          $this->_result['devices'][$group]['items'][0]['info'] = $this->_result['devices'][$group]['status'];
714
                      }
715
                } else {
716
                    $this->_result['devices'][$group]['items'][0]['status'] = "ok";
717
                }
718
            }
719
        }
720
    }
721
 
722
    private function execute_zpool($buffer)
723
    {
724
        $raiddata = preg_split("/(\r?\n)+ +(?=pool: )/", $buffer, -1, PREG_SPLIT_NO_EMPTY);
725
        if (!empty($raiddata)) foreach ($raiddata as $raid) {
726
            if (preg_match("/^pool: (\S+)/", $raid, $buff)) {
727
                $group = $buff[1];
728
                $this->_result['devices'][$group]['prog'] = "zpool";
729
                if (preg_match("/^ +state: (\S+)/m", $raid, $buff)) {
730
                    $this->_result['devices'][$group]['status'] = $buff[1];
731
                }
732
                $databegin = preg_split("/\n[ \t]+NAME +STATE +READ +WRITE +CKSUM\r?\n/", $raid, -1, PREG_SPLIT_NO_EMPTY);
733
                if (!empty($databegin) && (count($databegin)==2)) {
734
                    $datas = preg_split("/\r?\n[ \t]*\r?\n/", $databegin[1], -1, PREG_SPLIT_NO_EMPTY);
735
                    $datalines = preg_split("/\r?\n/", $datas[0], -1, PREG_SPLIT_NO_EMPTY);
736
                    $rootoffset = false;
737
                    $lastparentids = array(0=>-1);
738
                    $lastindent = 0;
739
                    $lastid = 0;
740
                    foreach ($datalines as $id=>$data) {
741
                        if (preg_match("/^([ \t]+)\S/", $data, $buff)) {;
742
                            $fullbuff = preg_split("/[ \t]+/", $data, 6, PREG_SPLIT_NO_EMPTY);
743
                            $offset=strlen($buff[1]);
744
                            if ($rootoffset === false) { // first line means root
745
                                $rootoffset = $offset;
746
                                $this->_result['devices'][$group]['items'][$id]['name'] = "";//$fullbuff[0];
747
                                if (count($fullbuff) > 1) {
748
                                    $this->_result['devices'][$group]['items'][$id]['status'] = $fullbuff[1];
749
                                }
750
                                $this->_result['devices'][$group]['items'][$id]['parentid'] = -2;
751
                                continue;
752
                            }
753
                            if ($offset < $rootoffset) { // some errors
754
                                continue;
755
                            }
756
 
757
                            $this->_result['devices'][$group]['items'][$id]['name'] = $fullbuff[0];
758
 
759
                            if (count($fullbuff) > 1) {
760
                                $this->_result['devices'][$group]['items'][$id]['status'] = $fullbuff[1];
761
                            }
762
                            if (count($fullbuff) > 5) {
763
                                $this->_result['devices'][$group]['items'][$id]['info'] = $fullbuff[5];
764
                            }
765
 
766
                            $indent = ($offset - $rootoffset)/2;
767
                            if ($indent > $lastindent) {
768
                                $lastparentids[$indent] = $lastid;
769
                            }
770
                            $this->_result['devices'][$group]['items'][$id]['parentid'] = $lastparentids[$indent];
771
 
772
                            if ($lastparentids[$indent] >= 0) {
773
                                if (isset($this->_result['devices'][$group]['items'][$lastparentids[$indent]]['childs'])) {
774
                                    $this->_result['devices'][$group]['items'][$lastparentids[$indent]]['childs']++;
775
                                } else {
776
                                    $this->_result['devices'][$group]['items'][$lastparentids[$indent]]['childs'] = 1;
777
                                }
778
                            }
779
 
780
                            $lastindent = $indent;
781
                            $lastid = $id;
782
                        }
783
                    }
784
                    foreach ($this->_result['devices'][$group]['items'] as $id=>$data) { // type analize
785
                        if ((!isset($data['childs']) || ($data['childs']<1)) && ($data['parentid']>=0) && !preg_match("/^mirror$|^mirror-|^spare$|^spare-|^replacing$|^replacing-|^raidz[123]$|^raidz[123]-/", $data['name'])) {
786
                            $this->_result['devices'][$group]['items'][$id]['type'] = "disk";
787
                        } elseif (isset($data['childs']) && !preg_match("/^spares$|^mirror$|^mirror-|^spare$|^spare-|^replacing$|^replacing-|^raidz[123]$|^raidz[123]-/", $data['name'])) {
788
                            if (($data['childs']==1) && ($data['parentid']==-2) && isset($this->_result['devices'][$group]['items'][$id+1]) && !preg_match("/^mirror$|^mirror-|^spare$|^spare-|^replacing$|^replacing-|^raidz[123]$|^raidz[123]-/", $this->_result['devices'][$group]['items'][$id+1]['name'])) {
789
                                $this->_result['devices'][$group]['items'][$id]['name2'] = "jbod";
790
                            } elseif ($data['childs']>1) {
791
                                $this->_result['devices'][$group]['items'][$id]['name2'] = "stripe";
792
                            }
793
                        }
794
                    }
795
 
796
                    foreach ($this->_result['devices'][$group]['items'] as $id=>$data) { // size optimize
797
                        if (($data['parentid']<0) && isset($data['childs']) && ($data['childs']==1) && (!isset($data['name2']) || ($data['name2']!=="jbod"))) {
798
                            if ($data['parentid']==-2) {
799
                                unset($this->_result['devices'][$group]['items'][$id]);
800
                            } elseif (($data['parentid'] == -1) && !isset($this->_result['devices'][$group]['items'][$id+1]['type'])) {
801
                                $this->_result['devices'][$group]['items'][$id+1]['name2'] = $data['name'];
802
                                $this->_result['devices'][$group]['items'][$id+1]['parentid'] = $data['parentid'];
803
                                unset($this->_result['devices'][$group]['items'][$id]);
804
                                foreach ($this->_result['devices'][$group]['items'] as $id2=>$data2) {
805
                                    if ($data2['parentid']>$id) {
806
                                        $this->_result['devices'][$group]['items'][$id2]['parentid'] = $data2['parentid'] - 1;
807
                                    }
808
                                }
809
                            }
810
                        }
811
                    }
812
 
813
                    if (isset($this->_result['devices'][$group]['items'][0])) {
814
                        $shift = true;
815
                    } else {
816
                        $shift = false;
817
                    }
818
                    foreach ($this->_result['devices'][$group]['items'] as $id=>$data) {
819
                        // reindex
820
                        if ($shift) {
821
                            $this->_result['devices'][$group]['items'][$id]['parentid']++;
822
                        }
823
                        if ($data['parentid']<0) {
824
                            $this->_result['devices'][$group]['items'][$id]['parentid'] = 0;
825
                        }
826
 
827
                         // name append
828
                        if (isset($data['name2'])) {
829
                            if (($data['name2']==="cache") || ($data['name2']==="logs")) {
830
                                $this->_result['devices'][$group]['items'][$id]['name'] = trim($data['name2']." ".$data['name']);
831
                            } else {
832
                                $this->_result['devices'][$group]['items'][$id]['name'] = trim($data['name']." ".$data['name2']);
833
                            }
834
                            unset($this->_result['devices'][$group]['items'][$id]['name2']);
835
                        }
836
 
837
                        // status and info normalize
838
                        if (isset($data['status'])) {
839
                                switch ($data['status']) {
840
                                    case 'AVAIL':
841
                                        if (isset($data['info'])) {
842
                                            $this->_result['devices'][$group]['items'][$id]['info'] = $data['status']." ".$data['info'];
843
                                        } else {
844
                                            $this->_result['devices'][$group]['items'][$id]['info'] = $data['status'];
845
                                        }
846
                                        $this->_result['devices'][$group]['items'][$id]['status'] = "S";
847
                                        break;
848
                                    case 'INUSE':
849
                                    case 'DEGRADED':
850
                                        if (isset($data['info'])) {
851
                                            $this->_result['devices'][$group]['items'][$id]['info'] = $data['status']." ".$data['info'];
852
                                        } else {
853
                                            $this->_result['devices'][$group]['items'][$id]['info'] = $data['status'];
854
                                        }
855
                                        $this->_result['devices'][$group]['items'][$id]['status'] = "W";
856
                                        break;
857
                                    case 'UNAVAIL':
858
                                    case 'FAULTED':
859
                                        if (isset($data['info'])) {
860
                                            $this->_result['devices'][$group]['items'][$id]['info'] = $data['status']." ".$data['info'];
861
                                        } else {
862
                                            $this->_result['devices'][$group]['items'][$id]['info'] = $data['status'];
863
                                        }
864
                                        $this->_result['devices'][$group]['items'][$id]['status'] = "F";
865
                                        break;
866
                                    default:
867
                                        $this->_result['devices'][$group]['items'][$id]['status'] = "ok";
868
                                }
869
                        } else {
870
                            if ($this->_result['devices'][$group]['items'][$id]['name'] == "spares") {
871
                                $this->_result['devices'][$group]['items'][$id]['status'] = "S";
872
                            } else {
873
                                $this->_result['devices'][$group]['items'][$id]['status'] = "ok";
874
                            }
875
                        }
876
                    }
877
                }
878
            }
879
        }
880
    }
881
 
882
    private function execute_idrac($buffer, $device)
883
    {
884
        $snmptablec = array(); //controller table
885
        $snmptableb = array(); //battery table
886
        $snmptablev = array(); //virtual disks table
887
        $snmptablep = array(); //physical disks table
888
 
889
        $buffer = preg_replace('/End of MIB\r?\n/', '', $buffer);
890
        $buffer = preg_replace('/\s\r?\n([^\.])/', ' $1', $buffer);
891
        $raiddata = preg_split("/\r?\n/", $buffer, -1, PREG_SPLIT_NO_EMPTY);
892
        if (!empty($raiddata)) {
893
            foreach ($raiddata as $line) {
894
                if (preg_match('/^(.+) = Hex-STRING:\s(.+)/', $line, $linetmp)) {
895
                    $hexchars = explode(" ", trim($linetmp[2]));
896
                    $newstring = "";
897
                    foreach ($hexchars as $hexchar) {
898
                        $hexint = hexdec($hexchar);
899
                        if (($hexint<32) || ($hexint>126)) {
900
                            $newstring .= ".";
901
                        } else {
902
                            $newstring .= chr($hexint);
903
                        }
904
                    }
905
                    if ($newstring!=="") {
906
                        $line = $linetmp[1]." = STRING: ".$newstring;
907
                    }
908
                }
909
                if (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.1\.1\.2\.(.*) = STRING:\s(.*)/', $line, $data)) {
910
                    $snmptablec[$data[1]]['controllerName']=trim($data[2], "\"");
911
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.1\.1\.8\.(.*) = STRING:\s(.*)/', $line, $data)) {
912
//                    $snmptablec[$data[1]]['controllerFWVersion']=trim($data[2], "\"");
913
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.1\.1\.9\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
914
                    $snmptablec[$data[1]]['controllerCacheSizeInMB']=$data[2];
915
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.1\.1\.37\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
916
                    $snmptablec[$data[1]]['controllerRollUpStatus']=$data[2];
917
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.1\.1\.78\.(.*) = STRING:\s(.*)/', $line, $data)) {
918
                    $snmptablec[$data[1]]['controllerFQDD']=trim($data[2], "\"");
919
 
920
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.15\.1\.4\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
921
                    $snmptableb[$data[1]]['batteryState']=$data[2];
922
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.15\.1\.6\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
923
//                    $snmptableb[$data[1]]['batteryComponentStatus']=$data[2];
924
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.15\.1\.20\.(.*) = STRING:\s(.*)/', $line, $data)) {
925
                    $snmptableb[$data[1]]['batteryFQDD']=trim($data[2], "\"");
926
 
927
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.2\.(.*) = STRING:\s(.*)/', $line, $data)) {
928
                    $snmptablep[$data[1]]['physicalDiskName']=trim($data[2], "\"");
929
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.4\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
930
                    $snmptablep[$data[1]]['physicalDiskState']=$data[2];
931
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.11\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
932
//                    $snmptablep[$data[1]]['physicalDiskCapacityInMB']=$data[2];
933
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.22\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
934
//                    $snmptablep[$data[1]]['physicalDiskSpareState']=$data[2];
935
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.24\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
936
//                    $snmptablep[$data[1]]['physicalDiskComponentStatus']=$data[2];
937
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.50\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
938
//                    $snmptablep[$data[1]]['physicalDiskOperationalState']=$data[2];
939
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.51\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
940
//                    $snmptablep[$data[1]]['physicalDiskProgress']=$data[2];
941
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.130\.4\.1\.54\.(.*) = STRING:\s(.*)/', $line, $data)) {
942
                    $snmptablep[$data[1]]['physicalDiskFQDD']=trim($data[2], "\"");
943
 
944
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.2\.(.*) = STRING:\s(.*)/', $line, $data)) {
945
                    $snmptablev[$data[1]]['virtualDiskName']=trim($data[2], "\"");
946
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.4\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
947
                    $snmptablev[$data[1]]['virtualDiskState']=$data[2];
948
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.6\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
949
                    $snmptablev[$data[1]]['virtualDiskSizeInMB']=$data[2];
950
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.10\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
951
                    $snmptablev[$data[1]]['virtualDiskWritePolicy']=$data[2];
952
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.11\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
953
                    $snmptablev[$data[1]]['virtualDiskReadPolicy']=$data[2];
954
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.13\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
955
                    $snmptablev[$data[1]]['virtualDiskLayout']=$data[2];
956
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.14\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
957
//                    $snmptablev[$data[1]]['virtualDiskStripeSize']=$data[2];
958
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.20\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
959
//                    $snmptablev[$data[1]]['virtualDiskComponentStatus']=$data[2];
960
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.23\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
961
                    $snmptablev[$data[1]]['virtualDiskBadBlocksDetected']=$data[2];
962
//                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.26\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
963
//                    $snmptablev[$data[1]]['virtualDiskDiskCachePolicy']=$data[2];
964
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.30\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
965
                    $snmptablev[$data[1]]['virtualDiskOperationalState']=$data[2];
966
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.31\.(.*) = INTEGER:\s(.*)/', $line, $data)) {
967
                    $snmptablev[$data[1]]['virtualDiskProgress']=$data[2];
968
                } elseif (preg_match('/^\.1\.3\.6\.1\.4\.1\.674\.10892\.5\.5\.1\.20\.140\.1\.1\.35\.(.*) = STRING:\s(.*)/', $line, $data)) {
969
                    $snmptablev[$data[1]]['virtualDiskFQDD']=trim($data[2], "\"");
970
                }
971
            }
972
 
973
            foreach ($snmptablec as $raid_controller) {
974
                $tablec = array(); //controller result table
975
                if (isset($raid_controller['controllerRollUpStatus'])) {
976
                    switch ($raid_controller['controllerRollUpStatus']) {
977
                        case 1:
978
                            $tablec['status'] = "W";
979
                            $tablec['info'] = "Other";
980
                            break;
981
                        case 2:
982
                            $tablec['status'] = "W";
983
                            $tablec['info'] = "Unknown";
984
                            break;
985
                        case 3:
986
                            $tablec['status'] ="ok";
987
                            break;
988
                        case 4:
989
                            $tablec['status'] ="W";
990
                            $tablec['info'] ="Non-critical";
991
                            break;
992
                        case 5:
993
                            $tablec['status'] = "F";
994
                            $tablec['info'] = "Critical";
995
                            break;
996
                        case 6:
997
                            $tablec['status'] = "F";
998
                            $tablec['info'] = "Non-recoverable";
999
                            break;
1000
                    }
1001
                }
1002
                if (isset($raid_controller['controllerName'])) {
1003
                    $tablec['controller'] = $raid_controller['controllerName'];
1004
                }
1005
                if (isset($raid_controller['controllerCacheSizeInMB'])) {
1006
                    $tablec['cache_size'] = $raid_controller['controllerCacheSizeInMB'] * 1024 * 1024;
1007
                }
1008
                foreach ($snmptableb as $raid_battery) {
1009
                    if (isset($raid_battery['batteryFQDD'])
1010
                       && isset($raid_controller['controllerFQDD'])
1011
                       && preg_match("/:".$raid_controller['controllerFQDD']."$/", $raid_battery['batteryFQDD'])) {
1012
                        if (isset($raid_battery['batteryState'])) {
1013
                            switch ($raid_battery['batteryState']) {
1014
                                case 1:
1015
                                    $tablec['battery'] = "unknown";
1016
                                    break;
1017
                                case 2:
1018
                                    $tablec['battery'] = "ready";
1019
                                    break;
1020
                                case 3:
1021
                                    $tablec['battery'] = "failed";
1022
                                    break;
1023
                                case 4:
1024
                                    $tablec['battery'] = "degraded";
1025
                                    break;
1026
                                case 5:
1027
                                    $tablec['battery'] = "missing";
1028
                                    break;
1029
                                case 6:
1030
                                    $tablec['battery'] = "charging";
1031
                                    break;
1032
                                case 7:
1033
                                    $tablec['battery'] = "bellowThreshold";
1034
                                    break;
1035
                            }
1036
                        }
1037
                        break;
1038
                    }
1039
                }
1040
                foreach ($snmptablep as $raid_physical) {
1041
                    if (isset($raid_physical['physicalDiskFQDD'])
1042
                       && isset($raid_controller['controllerFQDD'])
1043
                       && preg_match("/:".$raid_controller['controllerFQDD']."$/", $raid_physical['physicalDiskFQDD'])) {
1044
                        $devname = $device.'-'.preg_replace('/[a-zA-Z\.]/', '', $raid_controller['controllerFQDD']);
1045
                        $this->_result['devices'][$devname]['prog'] = 'idrac';
1046
                        $this->_result['devices'][$devname]['name']=$raid_controller['controllerFQDD'];
1047
                        if (isset($tablec['controller'])) {
1048
                            $this->_result['devices'][$devname]['controller'] = $tablec['controller'];
1049
                        }
1050
                        if (isset($tablec['battery'])) {
1051
                            $this->_result['devices'][$devname]['battery'] = $tablec['battery'];
1052
                        }
1053
                        if (isset($tablec['info'])) {
1054
                            $this->_result['devices'][$devname]['status'] = $tablec['info'];
1055
                        } elseif (isset($tablec['status'])) {
1056
                            $this->_result['devices'][$devname]['status'] = $tablec['status'];
1057
                        }
1058
                        $this->_result['devices'][$devname]['items'][0]['name']=$raid_controller['controllerFQDD'];
1059
                        $this->_result['devices'][$devname]['items'][0]['parentid'] = 0;
1060
                        if (isset($tablec['status'])) {
1061
                            $this->_result['devices'][$devname]['items'][0]['status'] = $tablec['status'];
1062
                            if (isset($tablec['info'])) {
1063
                                $this->_result['devices'][$devname]['items'][0]['info'] = $tablec['info'];
1064
                            }
1065
                        }
1066
                        $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['name']=$raid_physical['physicalDiskName'];
1067
                        $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['parentid'] = 1;
1068
                        $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['type'] = 'disk';
1069
 
1070
                        if (isset($raid_physical['physicalDiskState'])) {
1071
                            switch ($raid_physical['physicalDiskState']) {
1072
                                case 1:
1073
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "W";
1074
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "unknown";
1075
                                    break;
1076
                                case 2:
1077
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "W";
1078
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "ready";
1079
                                    break;
1080
                                case 3:
1081
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "ok";
1082
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "online";
1083
                                    break;
1084
                                case 4:
1085
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "W";
1086
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "foreign";
1087
                                    break;
1088
                                case 5:
1089
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "F";
1090
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "offline";
1091
                                    break;
1092
                                case 6:
1093
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "F";
1094
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "blocked";
1095
                                    break;
1096
                                case 7:
1097
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "F";
1098
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "failed";
1099
                                    break;
1100
                                case 8:
1101
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "S";
1102
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "non-raid";
1103
                                    break;
1104
                                case 9:
1105
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['status'] = "F";
1106
                                    $this->_result['devices'][$devname]['items'][$raid_physical['physicalDiskName']]['info'] = "removed";
1107
                                    break;
1108
                            }
1109
                        }
1110
                    }
1111
                }
1112
                foreach ($snmptablev as $raid_virtual) {
1113
                    if (isset($raid_virtual['virtualDiskFQDD'])
1114
                       && isset($raid_controller['controllerFQDD'])
1115
                       && preg_match("/:".$raid_controller['controllerFQDD']."$/", $raid_virtual['virtualDiskFQDD'])) {
1116
                        $devname = $device.'-'.preg_replace('/[a-zA-Z\.]/', '', $raid_virtual['virtualDiskFQDD']);
1117
                        $this->_result['devices'][$devname]['prog'] = 'idrac';
1118
                        $this->_result['devices'][$devname]['name']=$raid_virtual['virtualDiskFQDD'];
1119
                        $this->_result['devices'][$devname]['items'][0]['name']=$raid_virtual['virtualDiskFQDD'];
1120
                        $this->_result['devices'][$devname]['items'][0]['parentid'] = 0;
1121
                        if (isset($tablec['controller'])) {
1122
                            $this->_result['devices'][$devname]['controller'] = $tablec['controller'];
1123
                        }
1124
                        if (isset($tablec['battery'])) {
1125
                            $this->_result['devices'][$devname]['battery'] = $tablec['battery'];
1126
                        }
1127
                        if (isset($tablec['cache_size'])) {
1128
                            $this->_result['devices'][$devname]['cache_size'] = $tablec['cache_size'];
1129
                        }
1130
                        if (isset($raid_virtual['virtualDiskLayout'])) {
1131
                            switch ($raid_virtual['virtualDiskLayout']) {
1132
                                case 1:
1133
                                    $this->_result['devices'][$devname]['level'] = "other";
1134
                                    break;
1135
                                case 2:
1136
                                    $this->_result['devices'][$devname]['level'] = "raid0";
1137
                                    break;
1138
                                case 3:
1139
                                    $this->_result['devices'][$devname]['level'] = "raid1";
1140
                                    break;
1141
                                case 4:
1142
                                    $this->_result['devices'][$devname]['level'] = "raid5";
1143
                                    break;
1144
                                case 5:
1145
                                    $this->_result['devices'][$devname]['level'] = "raid6";
1146
                                    break;
1147
                                case 6:
1148
                                    $this->_result['devices'][$devname]['level'] = "raid10";
1149
                                    break;
1150
                                case 7:
1151
                                    $this->_result['devices'][$devname]['level'] = "raid50";
1152
                                    break;
1153
                                case 8:
1154
                                    $this->_result['devices'][$devname]['level'] = "raid60";
1155
                                    break;
1156
                                case 9:
1157
                                    $this->_result['devices'][$devname]['level'] = "concatraid1";
1158
                                    break;
1159
                                case 10:
1160
                                    $this->_result['devices'][$devname]['level'] = "concatraid5";
1161
                                    break;
1162
                                default:
1163
                                    $this->_result['devices'][$devname]['level'] = "unknown";
1164
                            }
1165
                            if (isset($this->_result['devices'][$devname]['level'])) {
1166
                                $this->_result['devices'][$devname]['items'][0]['name'] = $this->_result['devices'][$devname]['level'];
1167
                            }
1168
                        }
1169
                        if (isset($raid_virtual['virtualDiskState'])) {
1170
                            switch ($raid_virtual['virtualDiskState']) {
1171
                                case 1:
1172
                                    $this->_result['devices'][$devname]['status'] = "unknown";
1173
                                    $this->_result['devices'][$devname]['items'][0]['status']="W";
1174
                                    $this->_result['devices'][$devname]['items'][0]['info'] = $this->_result['devices'][$devname]['status'];
1175
                                    break;
1176
                                case 2:
1177
                                    $this->_result['devices'][$devname]['status'] = "online";
1178
                                    $this->_result['devices'][$devname]['items'][0]['status']="ok";
1179
                                    $this->_result['devices'][$devname]['items'][0]['info'] = $this->_result['devices'][$devname]['status'];
1180
                                    break;
1181
                                case 3:
1182
                                    $this->_result['devices'][$devname]['status'] = "failed";
1183
                                    $this->_result['devices'][$devname]['items'][0]['status']="F";
1184
                                    $this->_result['devices'][$devname]['items'][0]['info'] = $this->_result['devices'][$devname]['status'];
1185
                                    break;
1186
                                case 4:
1187
                                    $this->_result['devices'][$devname]['status'] = "degraded";
1188
                                    $this->_result['devices'][$devname]['items'][0]['status']="W";
1189
                                    $this->_result['devices'][$devname]['items'][0]['info'] = $this->_result['devices'][$devname]['status'];
1190
                                    break;
1191
                            }
1192
                        }
1193
                        if (isset($raid_virtual['virtualDiskOperationalState'])) {
1194
                            switch ($raid_virtual['virtualDiskOperationalState']) {
1195
                                case 1:
1196
                                    //$this->_result['devices'][$devname]['action']['name'] = "notApplicable";
1197
                                    break;
1198
                                case 2:
1199
                                    $this->_result['devices'][$devname]['action']['name'] = "reconstructing";
1200
                                    if (isset($raid_virtual['virtualDiskProgress'])) {
1201
                                        $this->_result['devices'][$devname]['action']['percent'] = $raid_virtual['virtualDiskProgress'];
1202
                                    } else {
1203
                                        $this->_result['devices'][$devname]['action']['percent'] = 0;
1204
                                    }
1205
                                    break;
1206
                                case 3:
1207
                                    $this->_result['devices'][$devname]['action']['name'] = "resyncing";
1208
                                    if (isset($raid_virtual['virtualDiskProgress'])) {
1209
                                        $this->_result['devices'][$devname]['action']['percent'] = $raid_virtual['virtualDiskProgress'];
1210
                                    } else {
1211
                                        $this->_result['devices'][$devname]['action']['percent'] = 0;
1212
                                    }
1213
                                    break;
1214
                                case 4:
1215
                                    $this->_result['devices'][$devname]['action']['name'] = "initializing";
1216
                                    if (isset($raid_virtual['virtualDiskProgress'])) {
1217
                                        $this->_result['devices'][$devname]['action']['percent'] = $raid_virtual['virtualDiskProgress'];
1218
                                    } else {
1219
                                        $this->_result['devices'][$devname]['action']['percent'] = 0;
1220
                                    }
1221
                                    break;
1222
                                case 5:
1223
                                    $this->_result['devices'][$devname]['action']['name'] = "backgroundInit";
1224
                                    if (isset($raid_virtual['virtualDiskProgress'])) {
1225
                                        $this->_result['devices'][$devname]['action']['percent'] = $raid_virtual['virtualDiskProgress'];
1226
                                    } else {
1227
                                        $this->_result['devices'][$devname]['action']['percent'] = 0;
1228
                                    }
1229
                                    break;
1230
                            }
1231
                        }
1232
                        if (isset($raid_virtual['virtualDiskSizeInMB'])) {
1233
                            $this->_result['devices'][$devname]['size'] = $raid_virtual['virtualDiskSizeInMB'] * 1024 * 1024;
1234
                        }
1235
 
1236
                        if (isset($raid_virtual['virtualDiskReadPolicy'])) {
1237
                            switch ($raid_virtual['virtualDiskReadPolicy']) {
1238
                                case 1:
1239
                                    $this->_result['devices'][$devname]['readpolicy'] = "noReadAhead";
1240
                                    break;
1241
                                case 2:
1242
                                    $this->_result['devices'][$devname]['readpolicy'] = "readAhead";
1243
                                    break;
1244
                                case 3:
1245
                                    $this->_result['devices'][$devname]['readpolicy'] = "adaptiveReadAhead";
1246
                                    break;
1247
                            }
1248
                        }
1249
                        if (isset($raid_virtual['virtualDiskWritePolicy'])) {
1250
                            switch ($raid_virtual['virtualDiskWritePolicy']) {
1251
                                case 1:
1252
                                    $this->_result['devices'][$devname]['writepolicy'] = "writeThrough";
1253
                                    break;
1254
                                case 2:
1255
                                    $this->_result['devices'][$devname]['writepolicy'] = "writeBack";
1256
                                    break;
1257
                                case 3:
1258
                                    $this->_result['devices'][$devname]['writepolicy'] = "writeBackForce";
1259
                                    break;
1260
                            }
1261
                        }
1262
                        if (isset($raid_virtual['virtualDiskState'])) {
1263
                            switch ($raid_virtual['virtualDiskState']) {
1264
                                case 1:
1265
                                    $this->_result['devices'][$devname]['status'] = "unknown";
1266
                                    break;
1267
                                case 2:
1268
                                    $this->_result['devices'][$devname]['status'] = "online";
1269
                                    break;
1270
                                case 3:
1271
                                    $this->_result['devices'][$devname]['status'] = "failed";
1272
                                    break;
1273
                                case 4:
1274
                                    $this->_result['devices'][$devname]['status'] = "degraded";
1275
                                    break;
1276
                            }
1277
                        }
1278
                        if (isset($raid_virtual['virtualDiskBadBlocksDetected'])) {
1279
                            $this->_result['devices'][$devname]['bad_blocks'] = $raid_virtual['virtualDiskBadBlocksDetected'];
1280
                        }
1281
                    }
1282
                }
1283
            }
1284
        }
1285
    }
1286
 
1287
    /**
1288
     * doing all tasks to get the required informations that the plugin needs
1289
     * result is stored in an internal array<br>the array is build like a tree,
1290
     * so that it is possible to get only a specific process with the childs
1291
     *
1292
     * @return void
1293
     */
1294
    public function execute()
1295
    {
1296
        if (count($this->_filecontent)>0) {
1297
            foreach ($this->prog_items as $item) if (isset($this->_filecontent[$item])) {
1298
                if ($item !== 'idrac') {
1299
                    if (!is_null($buffer = $this->_filecontent[$item]) && (($buffer = trim($buffer)) != "")) {
1300
                        switch ($item) {
1301
                            case 'mdstat':
1302
                                $this->execute_mdstat($buffer);
1303
                                break;
1304
                            case 'dmraid':
1305
                                $this->execute_dmraid($buffer);
1306
                                break;
1307
                            case 'megactl':
1308
                                $this->execute_megactl($buffer, false);
1309
                                break;
1310
                            case 'megasasctl':
1311
                                $this->execute_megactl($buffer, true);
1312
                                break;
1313
                            case 'graid':
1314
                                $this->execute_graid($buffer);
1315
                                break;
1316
                            case 'zpool':
1317
                                $this->execute_zpool($buffer);
1318
                                break;
1319
                        }
1320
                    }
1321
                } else {
1322
                    if (is_array($this->_filecontent[$item])) {
1323
                        foreach ($this->_filecontent[$item] as $device=>$buffer) if (($buffer = trim($buffer)) != "") {
1324
                            $this->execute_idrac($buffer, /*'idrac-'.*/$device);
1325
                        }
1326
                    }
1327
                }
1328
            }
1329
        }
1330
    }
1331
 
1332
    /**
1333
     * generates the XML content for the plugin
1334
     *
1335
     * @return SimpleXMLElement entire XML content for the plugin
1336
     */
1337
    public function xml()
1338
    {
1339
        if (empty($this->_result)) {
1340
            return $this->xml->getSimpleXmlElement();
1341
        }
1342
        $hideRaids = array();
1343
        if (defined('PSI_PLUGIN_RAID_HIDE_DEVICES') && is_string(PSI_PLUGIN_RAID_HIDE_DEVICES)) {
1344
            if (preg_match(ARRAY_EXP, PSI_PLUGIN_RAID_HIDE_DEVICES)) {
1345
                $hideRaids = eval(PSI_PLUGIN_RAID_HIDE_DEVICES);
1346
            } else {
1347
                $hideRaids = array(PSI_PLUGIN_RAID_HIDE_DEVICES);
1348
            }
1349
        }
1350
        foreach ($this->_result['devices'] as $key=>$device) {
1351
            if (!in_array(ltrim($key, "/"), $hideRaids, true)) {
1352
                $dev = $this->xml->addChild("Raid");
1353
                $dev->addAttribute("Device_Name", ltrim($key, "/")); //for megactl and megasasctl conflicts
1354
                $dev->addAttribute("Program", $device["prog"]);
1355
                if (isset($device['level'])) $dev->addAttribute("Level", strtolower($device["level"]));
1356
                $dev->addAttribute("Status", strtolower($device["status"]));
1357
                if (isset($device['name'])) $dev->addAttribute("Name", $device["name"]);
1358
                if (isset($device['size'])) $dev->addAttribute("Size", $device["size"]);
1359
                if (isset($device['stride'])) $dev->addAttribute("Stride", $device["stride"]);
1360
                if (isset($device['subsets'])) $dev->addAttribute("Subsets", $device["subsets"]);
1361
                if (isset($device['devs'])) $dev->addAttribute("Devs", $device["devs"]);
1362
                if (isset($device['spares'])) $dev->addAttribute("Spares", $device["spares"]);
1363
 
1364
                if (isset($device['chunk_size'])) $dev->addAttribute("Chunk_Size", $device["chunk_size"]);
1365
                if (isset($device['pers_superblock'])) $dev->addAttribute("Persistend_Superblock", $device["pers_superblock"]);
1366
                if (isset($device['algorithm'])) $dev->addAttribute("Algorithm", $device["algorithm"]);
1367
                if (isset($device['registered'])) $dev->addAttribute("Disks_Registered", $device["registered"]);
1368
                if (isset($device['active'])) $dev->addAttribute("Disks_Active", $device["active"]);
1369
                if (isset($device['controller'])) $dev->addAttribute("Controller", $device["controller"]);
1370
                if (isset($device['battery'])) $dev->addAttribute("Battery", $device["battery"]);
1371
                if (isset($device['supported'])) $dev->addAttribute("Supported", $device["supported"]);
1372
                if (isset($device['readpolicy'])) $dev->addAttribute("ReadPolicy", $device["readpolicy"]);
1373
                if (isset($device['writepolicy'])) $dev->addAttribute("WritePolicy", $device["writepolicy"]);
1374
                if (isset($device['cache_size'])) $dev->addAttribute("Cache_Size", $device["cache_size"]);
1375
                if (isset($device['bad_blocks'])) $dev->addAttribute("Bad_Blocks", $device["bad_blocks"]);
1376
 
1377
                if (isset($device['action'])) {
1378
                    $action = $dev->addChild("Action");
1379
                    $action->addAttribute("Name", $device['action']['name']);
1380
                    if (isset($device['action']['percent'])) $action->addAttribute("Percent", $device['action']['percent']);
1381
 
1382
                    if (isset($device['action']['finish_time'])) $action->addAttribute("Time_To_Finish", $device['action']['finish_time']);
1383
                    if (isset($device['action']['finish_unit'])) $action->addAttribute("Time_Unit", $device['action']['finish_unit']);
1384
 
1385
                }
1386
                $disks = $dev->addChild("RaidItems");
1387
                if (isset($device['items']) && (sizeof($device['items'])>0)) foreach ($device['items'] as $disk) {
1388
                    if (isset($disk['name'])) {
1389
                        $disktemp = $disks->addChild("Item");
1390
                        $disktemp->addAttribute("Name", $disk['name']);
1391
                        // if (isset($disk['raid_index'])) $disktemp->addAttribute("Index", $disk['raid_index']);
1392
                        if (isset($disk['parentid'])) $disktemp->addAttribute("ParentID", $disk['parentid']);
1393
                        if (isset($disk['type'])) $disktemp->addAttribute("Type", $disk['type']);
1394
                        // if (in_array(strtolower($device["status"]), array('ok', 'optimal', 'active', 'online', 'degraded'))) {
1395
                            $disktemp->addAttribute("Status", $disk['status']);
1396
                        //} else {
1397
                        //    $disktemp->addAttribute("Status", "W");
1398
                        //}
1399
                        if (isset($disk['info'])) $disktemp->addAttribute("Info", $disk['info']);
1400
                    }
1401
                }
1402
            }
1403
        }
1404
 
1405
        return $this->xml->getSimpleXmlElement();
1406
    }
1407
}