"Fossies" - the Fresh Open Source Software Archive

Member "netxms-3.8.166/src/agent/subagents/ups/microdowell.cpp" (23 Feb 2021, 8237 Bytes) of package /linux/misc/netxms-3.8.166.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "microdowell.cpp" see the Fossies "Dox" file reference documentation.

    1 /*
    2 ** NetXMS UPS management subagent
    3 ** Copyright (C) 2006-2014 Alex Kirhenshtein
    4 **
    5 ** This program is free software; you can redistribute it and/or modify
    6 ** it under the terms of the GNU General Public License as published by
    7 ** the Free Software Foundation; either version 2 of the License, or
    8 ** (at your option) any later version.
    9 **
   10 ** This program is distributed in the hope that it will be useful,
   11 ** but WITHOUT ANY WARRANTY; without even the implied warranty of
   12 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   13 ** GNU General Public License for more details.
   14 **
   15 ** You should have received a copy of the GNU General Public License
   16 ** along with this program; if not, write to the Free Software
   17 ** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
   18 **
   19 **/
   20 
   21 #include "ups.h"
   22 
   23 #define VAL(x) ((unsigned char)buff[x+1] + (unsigned char)buff[x]*256)
   24 
   25 /**
   26  * Constructor
   27  */
   28 MicrodowellInterface::MicrodowellInterface(const TCHAR *device) : SerialInterface(device)
   29 {
   30     if (m_portSpeed == 0)
   31         m_portSpeed = 19200;
   32 }
   33 
   34 /**
   35  * Prepare and send data packet
   36  */
   37 BOOL MicrodowellInterface::sendCmd(const char *cmd, int cmdLen, char *ret, int *retLen)
   38 {
   39     char buff[512];
   40     int i, crc;
   41     int c;
   42 
   43     *retLen = 0;
   44     cmdLen &= 0xFF;
   45     buff[0] = '[';
   46     buff[1] = cmdLen;
   47     memcpy(buff + 2, cmd, cmdLen);
   48     for (i = 1, crc = 0; cmdLen >= 0; i++, cmdLen--)
   49     {
   50         crc ^= buff[i];
   51     }
   52     buff[i++] = crc;
   53 
   54    m_serial.write(buff, i);
   55 
   56     for (c = 0; c != '['; )
   57     {
   58         if (m_serial.read((char *)&c, 1) != 1)
   59         {
   60             return FALSE;
   61         }
   62     }
   63 
   64     if (m_serial.read(buff, i + 1) < i + 1)
   65     {
   66         return FALSE;
   67     }
   68 
   69     for (crc = i, c = 0; c < i; c++)
   70     {
   71         crc ^= buff[c];
   72     }
   73 
   74     if (crc != buff[c])
   75     {
   76         return FALSE;
   77     }
   78 
   79     memcpy(ret, buff, i);
   80     *retLen = i;
   81 
   82     return TRUE;
   83 }
   84 
   85 /**
   86  * Open device
   87  */
   88 BOOL MicrodowellInterface::open()
   89 {
   90    BOOL bRet = FALSE;
   91 
   92    if (!SerialInterface::open())
   93       return FALSE;
   94 
   95    m_serial.setTimeout(1000);
   96    m_serial.set(m_portSpeed, m_dataBits, m_parity, m_stopBits);
   97 
   98     char buff[512];
   99     int len;
  100     if (sendCmd("\x50\x80\x08", 3, buff, &len))
  101     {
  102         buff[11] = 0;
  103         if (buff[3] != 'E' || buff[4] != 'N' || buff[5] != 'T')
  104         {
  105             AgentWriteLog(EVENTLOG_WARNING_TYPE, _T("Unknown Microdowell UPS model on port %s (%hs)"), m_device, buff);
  106         }
  107         else
  108         {
  109             bRet = TRUE;
  110             setConnected();
  111         }
  112 
  113         ge2kva = buff[4] > '2' || ( buff[4] == '2' && buff[5] > '0' );
  114     }
  115 
  116    return bRet;
  117 }
  118 
  119 /**
  120  * Validate connection
  121  */
  122 BOOL MicrodowellInterface::validateConnection()
  123 {
  124    BOOL bRet = TRUE;
  125     char buff[512];
  126     int len;
  127 
  128     if (!sendCmd("\x00", 1, buff, &len))
  129     {
  130         bRet = FALSE;
  131     }
  132 
  133    return bRet;
  134 }
  135 
  136 /**
  137  * Get UPS model
  138  */
  139 void MicrodowellInterface::queryModel()
  140 {
  141     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_MODEL];
  142 
  143     char buff[512];
  144     int len;
  145     if (sendCmd("\x50\x80\x08", 3, buff, &len))
  146     {
  147         buff[11] = 0;
  148         strcpy(p->szValue, buff + 1);
  149       p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  150     }
  151     else
  152     {
  153         p->dwFlags |= UPF_NULL_VALUE;
  154     }
  155 }
  156 
  157 
  158 //
  159 // Get UPS firmware version
  160 //
  161 
  162 void MicrodowellInterface::queryFirmwareVersion()
  163 {
  164     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_FIRMWARE];
  165 
  166     p->dwFlags |= UPF_NOT_SUPPORTED;
  167 }
  168 
  169 
  170 //
  171 // Get manufacturing date
  172 //
  173 
  174 void MicrodowellInterface::queryMfgDate()
  175 {
  176     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_MFG_DATE];
  177 
  178     char buff[512];
  179     int len;
  180     if (sendCmd("\x50\xA0\x08", 3, buff, &len))
  181     {
  182         buff[11] = 0;
  183         snprintf(p->szValue, MAX_RESULT_LENGTH, "%d/%d/%d", buff[4], buff[5], buff[3]);
  184       p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  185     }
  186     else
  187     {
  188         p->dwFlags |= UPF_NULL_VALUE;
  189     }
  190 }
  191 
  192 
  193 //
  194 // Get serial number
  195 //
  196 
  197 void MicrodowellInterface::querySerialNumber()
  198 {
  199     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_SERIAL];
  200     char buff[512];
  201     int len;
  202     if (sendCmd("\x50\x98\x08", 3, buff, &len))
  203     {
  204         buff[11] = 0;
  205         strcpy(p->szValue, buff + 1);
  206         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  207     }
  208     else
  209     {
  210         p->dwFlags |= UPF_NULL_VALUE;
  211     }
  212 }
  213 
  214 
  215 //
  216 // Get temperature inside UPS
  217 //
  218 
  219 void MicrodowellInterface::queryTemperature()
  220 {
  221     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_TEMP];
  222 
  223     char buff[512];
  224     int len;
  225     if (sendCmd("\x01", 1, buff, &len))
  226     {
  227         snprintf(p->szValue, MAX_RESULT_LENGTH, "%.1f", ((float)VAL(11)  - 202.97) / 1.424051);
  228         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  229     }
  230     else
  231     {
  232         p->dwFlags |= UPF_NULL_VALUE;
  233     }
  234 }
  235 
  236 
  237 //
  238 // Get battery voltage
  239 //
  240 
  241 void MicrodowellInterface::queryBatteryVoltage()
  242 {
  243     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_BATTERY_VOLTAGE];
  244 
  245     char buff[512];
  246     int len;
  247     if (sendCmd("\x01", 1, buff, &len))
  248     {
  249         snprintf(p->szValue, MAX_RESULT_LENGTH, "%.1f", (float)VAL(3) / 36.4);
  250         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  251     }
  252     else
  253     {
  254         p->dwFlags |= UPF_NULL_VALUE;
  255     }
  256 }
  257 
  258 
  259 //
  260 // Get nominal battery voltage
  261 //
  262 
  263 void MicrodowellInterface::queryNominalBatteryVoltage()
  264 {
  265     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_NOMINAL_BATT_VOLTAGE];
  266     p->dwFlags |= UPF_NOT_SUPPORTED;
  267 }
  268 
  269 
  270 //
  271 // Get battery level (in percents)
  272 //
  273 
  274 void MicrodowellInterface::queryBatteryLevel()
  275 {
  276     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_BATTERY_LEVEL];
  277 
  278     char buff[512];
  279     int len;
  280     if (sendCmd("\x03", 1, buff, &len))
  281     {
  282         snprintf(p->szValue, MAX_RESULT_LENGTH, "%d", (int)buff[1]);
  283         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  284     }
  285     else
  286     {
  287         p->dwFlags |= UPF_NULL_VALUE;
  288     }
  289 }
  290 
  291 
  292 //
  293 // Get input line voltage
  294 //
  295 
  296 void MicrodowellInterface::queryInputVoltage()
  297 {
  298     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_INPUT_VOLTAGE];
  299 
  300     char buff[512];
  301     int len;
  302     if (sendCmd("\x01", 1, buff, &len))
  303     {
  304         snprintf(p->szValue, MAX_RESULT_LENGTH, "%.1f", (float)VAL(3) / 36.4);
  305         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  306     }
  307     else
  308     {
  309         p->dwFlags |= UPF_NULL_VALUE;
  310     }
  311 }
  312 
  313 
  314 //
  315 // Get output voltage
  316 //
  317 
  318 void MicrodowellInterface::queryOutputVoltage()
  319 {
  320     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_OUTPUT_VOLTAGE];
  321 
  322     char buff[512];
  323     int len;
  324     if (sendCmd("\x01", 1, buff, &len))
  325     {
  326         snprintf(p->szValue, MAX_RESULT_LENGTH, "%.1f", (float)VAL(7) / (ge2kva ? 63.8 : 36.4));
  327         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  328     }
  329     else
  330     {
  331         p->dwFlags |= UPF_NULL_VALUE;
  332     }
  333 }
  334 
  335 
  336 //
  337 // Get line frequency (Hz)
  338 //
  339 
  340 void MicrodowellInterface::queryLineFrequency()
  341 {
  342     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_LINE_FREQ];
  343 
  344     char buff[512];
  345     int len;
  346     if (sendCmd("\x03", 1, buff, &len) && VAL(8))
  347     {
  348         snprintf(p->szValue, MAX_RESULT_LENGTH, "%d", (int)(50000.0 / VAL(8)));
  349         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  350     }
  351     else
  352     {
  353         p->dwFlags |= UPF_NULL_VALUE;
  354     }
  355 }
  356 
  357 
  358 //
  359 // Get UPS power load (in percents)
  360 //
  361 
  362 void MicrodowellInterface::queryPowerLoad()
  363 {
  364     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_LOAD];
  365 
  366     char buff[512];
  367     int len;
  368     if (sendCmd("\x03", 1, buff, &len))
  369     {
  370         snprintf(p->szValue, MAX_RESULT_LENGTH, "%d", (int)buff[7]);
  371         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  372     }
  373     else
  374     {
  375         p->dwFlags |= UPF_NULL_VALUE;
  376     }
  377 }
  378 
  379 
  380 //
  381 // Get estimated on-battery runtime
  382 //
  383 
  384 void MicrodowellInterface::queryEstimatedRuntime()
  385 {
  386     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_EST_RUNTIME];
  387 
  388     char buff[512];
  389     int len;
  390     if (sendCmd("\x03", 1, buff, &len) && VAL(2) != 65535)
  391     {
  392         snprintf(p->szValue, MAX_RESULT_LENGTH, "%d", VAL(2));
  393         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  394     }
  395     else
  396     {
  397         p->dwFlags |= UPF_NULL_VALUE;
  398     }
  399 }
  400 
  401 
  402 //
  403 // Check if UPS is online or on battery power
  404 //
  405 
  406 void MicrodowellInterface::queryOnlineStatus()
  407 {
  408     UPS_PARAMETER *p = &m_paramList[UPS_PARAM_ONLINE_STATUS];
  409 
  410     char buff[512];
  411     int len;
  412     if (sendCmd("\x00", 1, buff, &len))
  413     {
  414         p->szValue[1] = 0;
  415         p->dwFlags &= ~(UPF_NOT_SUPPORTED | UPF_NULL_VALUE);
  416         if (buff[1] & 0x10) // online
  417         {
  418             p->szValue[0] = '0';
  419         }
  420         else if (buff[1] & 0x01) // on battery
  421         {
  422             p->szValue[0] = '1';
  423         }
  424         else if (buff[1] & 0x02) // low battery
  425         {
  426             p->szValue[0] = '2';
  427         }
  428         else // unknown
  429         {
  430             p->dwFlags |= UPF_NULL_VALUE;
  431         }
  432     }
  433     else
  434     {
  435         p->dwFlags |= UPF_NULL_VALUE;
  436     }
  437 }
  438 
  439 ///////////////////////////////////////////////////////////////////////////////
  440 /*
  441 
  442 $Log: not supported by cvs2svn $
  443 Revision 1.3  2007/04/17 19:04:54  alk
  444 microdowell fixed(?). should test on a real hardware
  445 
  446 Revision 1.2  2006/12/09 21:02:11  victor
  447 New configure works on Gentoo Linux
  448 
  449 Revision 1.1  2006/12/05 13:20:15  alk
  450 Microdowell UPS support added
  451 
  452 
  453 */