{"action":"created","comment":{"url":"https://api.github.com/repos/neoclust/pulse/pulls/comments/65359442","id":65359442,"diff_hunk":"@@ -1,675 +1,675 @@\n-#!/usr/bin/python\r\n-# -*- coding: utf-8; -*-\r\n-#\r\n-# (c) 2007-2009 Mandriva, http://www.mandriva.com/\r\n-#\r\n-# $Id: improve.py 90 2008-04-8 09:24:56Z neisen $\r\n-#\r\n-# This file is part of Pulse 2, http://pulse2.mandriva.org\r\n-#\r\n-# Pulse 2 is free software; you can redistribute it and/or modify\r\n-# it under the terms of the GNU General Public License as published by\r\n-# the Free Software Foundation; either version 2 of the License, or\r\n-# (at your option) any later version.\r\n-#\r\n-# Pulse 2 is distributed in the hope that it will be useful,\r\n-# but WITHOUT ANY WARRANTY; without even the implied warranty of\r\n-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r\n-# GNU General Public License for more details.\r\n-#\r\n-# You should have received a copy of the GNU General Public License\r\n-# along with Pulse 2; if not, write to the Free Software\r\n-# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,\r\n-# MA 02110-1301, USA.\r\n-\r\n-'''\r\n-This is the module to add information to OCS XML\r\n-for the Windows platforms\r\n-'''\r\n-\r\n-import wmi\r\n-import _winreg\r\n-import os\r\n-import xml.dom.minidom\r\n-\r\n-from pulse2.proxyssl.config import Pulse2InventoryProxyConfig\r\n-\r\n-if Pulse2InventoryProxyConfig().addicon:\r\n-    import win32ui\r\n-    import win32gui\r\n-    import win32con\r\n-    import win32api\r\n-    import cStringIO\r\n-    import Image    # need install PIL package http://www.pythonware.com/products/pil/\r\n-    import base64\r\n-    import tempfile\r\n-    \r\n-    #system icon size \r\n-    ico_x = win32api.GetSystemMetrics(win32con.SM_CXICON)\r\n-    \r\n-    #tempory file\r\n-    tmpfile = tempfile.mkstemp()\r\n-    dirTmpFile = tmpfile[1] \r\n-    #close the opened temp file (SaveBitmapFile Error)   \r\n-    file = os.fdopen(tmpfile[0])\r\n-    file.close()\r\n-\r\n-'''    \r\n-Get the icon of file\r\n-@param path: the path of the file\r\n-@param nIcon: position of the icon in the file\r\n-@param exeOrDll=True: set False if is a icon file \r\n-@return string bit of icon in Jpeg Format encoded in base64, else Error : None\r\n-'''    \r\n-def windowsIconGetter(path, nIcon = 0 , exeOrDll = True):  #It's can be exe, dll, or already ico\r\n-    \r\n-    if os.path.isfile(path):\r\n-        dst = cStringIO.StringIO()\r\n-        if exeOrDll:\r\n-            large, small = win32gui.ExtractIconEx(path,nIcon)\r\n-            win32gui.DestroyIcon(small[0])\r\n-            #creating a destination memory DC \r\n-            hdc = win32ui.CreateDCFromHandle( win32gui.GetDC(0) )\r\n-            hbmp = win32ui.CreateBitmap()\r\n-            hbmp.CreateCompatibleBitmap(hdc, ico_x, ico_x)\r\n-            hdc = hdc.CreateCompatibleDC()\r\n-            hdc.SelectObject( hbmp )\r\n-            #set the background in white\r\n-            hdc.FillSolidRect( (0,0,ico_x,ico_x), 0xffffff )\r\n-            #draw a icon in it\r\n-            hdc.DrawIcon( (0,0), large[0] )\r\n-            win32gui.DestroyIcon(large[0])\r\n-            #convert picture in JPEG\r\n-            hbmp.SaveBitmapFile( hdc, dirTmpFile)\r\n-            im = Image.open(dirTmpFile)\r\n-        else:\r\n-            im = Image.open(path)\r\n-        \r\n-        try:\r\n-            im.save(dst, \"JPEG\")\r\n-        except IOError:\r\n-            return None\r\n-                \r\n-        dst.seek(0)\r\n-        return base64.b64encode( dst.read() )   \r\n-    \r\n-    else:    \r\n-        return None \r\n- \r\n-'''\r\n-Convert the Registry Date in Humain format date DD/MM/YYYY HH:MM:SS\r\n-@param date: date in registry format to convert\r\n-@param displayHour=True: if the registry date have no reached hour, set False to doesn't get 00:00:00\r\n-@return: convert date\r\n-'''\r\n-def windowsDateConversion(date, displayHour = True):\r\n-\r\n-    if (len(date)==8 or len(date)==25):     # check if it's good windows date system\r\n-        finaldate = date[6:8]+\"/\"+date[4:6]+\"/\"+date[0:4]\r\n-        if displayHour:\r\n-            finaldate = finaldate +\" \"+date[8:10]+\":\"+date[10:12]+\":\"+date[12:14]\r\n-    else:   # if the date is not in registry format\r\n-        finaldate = date\r\n-    \r\n-    return finaldate\r\n-\r\n-'''\r\n-Calculate the size of folder\r\n-@param folder: the path of the folder to calculate\r\n-@return: the size of the folder in Ko \r\n-'''\r\n-def sizeFolder(folder):\r\n-    size = 0\r\n-    for (current, subFolder, files) in os.walk(folder):\r\n-        size = size + sum( os.path.getsize( os.path.join(current, file) ) for file in files )\r\n-    return size/1024 #Ko\r\n-\r\n-'''\r\n-Search the information to add\r\n-@return: Dictonary with information asked\r\n-'''\r\n-def informationSearch():            # Found any information for the computer.\r\n-    result = {}                     # Software infomration will be reached in next time\r\n-    \r\n-    #With WMI\r\n-    wmiObject = wmi.WMI()\r\n-    \r\n-    #Company Register\r\n-    try:\r\n-        companyRegister = wmiObject.Win32_OperatingSystem([\"Organization\"])[0].Organization\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        companyRegister = \"N/A\"\r\n-        \r\n-    result['companyRegister']=companyRegister\r\n-    \r\n-    #Os Architecture (32-64 bit) only for Vista and superior\r\n-    try:\r\n-        osArchitecture = wmiObject.Win32_OperatingSystem([\"OSArchitecture\"])[0].OSArchitecture\r\n-    except WindowsError: # pyflakes.ignore\r\n-        osArchitecture = \"N/A\"\r\n-    except wmi.x_wmi :    # If os is XP, 2003, 2000, 98, 95, ...\r\n-        osArchitecture = \"32-bit\"\r\n-        \r\n-    result['osArchitecture']=osArchitecture\r\n-    \r\n-    # First boot\r\n-    try:\r\n-        dateFirst = wmiObject.Win32_BIOS([\"ReleaseDate\"])[0].ReleaseDate\r\n-        dateFirst = windowsDateConversion(dateFirst,False)\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        dateFirst = \"N/A\"\r\n-        \r\n-    result['dateFirst']=dateFirst\r\n-    \r\n-    # Last boot\r\n-    try:    \r\n-        dateLastBoot = wmiObject.Win32_OperatingSystem([\"LastBootUpTime\"])[0].LastBootUpTime\r\n-        dateLastBoot = windowsDateConversion(dateLastBoot)\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        dateLastBoot = \"N/A\"\r\n-        \r\n-    result['dateLastBoot'] = dateLastBoot\r\n-    \r\n-    # Serial Number\r\n-    try:  \r\n-        serialNumber = wmiObject.Win32_BIOS([\"SerialNumber\"])[0].SerialNumber\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        serialNumber = \"N/A\"\r\n-           \r\n-    result['serialNumber'] = serialNumber\r\n-    \r\n-    # Operating system installation date\r\n-    try:    \r\n-        dateInstall = wmiObject.Win32_OperatingSystem([\"InstallDate\"])[0].InstallDate\r\n-        dateInstall = windowsDateConversion(dateInstall)\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        dateInstall = \"N/A\"\r\n-        \r\n-    result['installDate'] = dateInstall\r\n-    \r\n-    # Default Gateway\r\n-    try:    \r\n-        interfacesAdapter = wmiObject.Win32_NetworkAdapterConfiguration([\"DefaultIPGateway\"])\r\n-        for interface in interfacesAdapter:\r\n-            if not (interface.DefaultIPGateway is None):\r\n-                defaultGateway = interface.DefaultIPGateway[0]\r\n-                break\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        defaultGateway = \"N/A\"\r\n-        \r\n-    result['defaultGateway'] = defaultGateway\r\n-        \r\n-        \r\n-    # Operating system folder\r\n-    try:\r\n-        # os.getenv(\"windir\")\r\n-        result['OSfolder'] = wmiObject.Win32_OperatingSystem([\"WindowsDirectory\"])[0].WindowsDirectory     #by WMI. The installation can be anywhere\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        result['OSfolder'] = \"N/A\"    \r\n-        \r\n-    # last login date\r\n-    wmiObject = wmi.WMI(privileges=[\"Security\"])\r\n-    try:\r\n-        lastLoginLog = wmiObject.Win32_NTLogEvent([\"InsertionStrings\",\"TimeGenerated\"],EventCode=680)[0]    # For Win XP et 2k, EventCode = 680, but with Vista EventCode = 4624\r\n-        lastLogin = [lastLoginLog.InsertionStrings[1],lastLoginLog.TimeGenerated]\r\n-        # convert the date\r\n-        lastLogin[1] = windowsDateConversion(lastLogin[1])\r\n-        result['lastLogin']=lastLogin\r\n-    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\r\n-        result['lastLogin']=[\"N/A\",\"N/A\"]\r\n-    \r\n-    return result\r\n-    \r\n-'''\r\n-Improve the xml File with the Information and another research\r\n-@param xmlString: the xml String of the xml file to improve\r\n-@param lastInformation: some information to add in xml\r\n-@return: the improving xmlString \r\n-'''\r\n-def xmlUpdate(xmlString, lastInformation):\r\n-    \r\n-    xmlFile = xml.dom.minidom.parseString(xmlString)\r\n-    \r\n-    # Check Serial number between Ocs and WMI\r\n-    ssn = xmlFile.getElementsByTagName(\"SSN\")[0].childNodes[0].nodeValue\r\n-    if ( len(lastInformation['serialNumber']) > 0 and ssn != lastInformation['serialNumber'] ):\r\n-        ssn = lastInformation['serialNumber']\r\n-        \r\n-    # Operating system installation date\r\n-    newnode = xmlFile.createElement(\"INSTALLDATE\")\r\n-    newtext = xmlFile.createTextNode(lastInformation['installDate'])\r\n-    refnode = xmlFile.getElementsByTagName(\"OSVERSION\")[0]\r\n-    \r\n-    newnode.appendChild(newtext)\r\n-    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\r\n-    #Optionnal : help to the final xml File can be easy read\r\n-    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode)    \r\n-    \r\n-    \r\n-    # Company Register\r\n-    newnode = xmlFile.createElement(\"WINCOMPANY\")\r\n-    newtext = xmlFile.createTextNode(lastInformation['companyRegister'])\r\n-    refnode = xmlFile.getElementsByTagName(\"WINOWNER\")[0]\r\n-    \r\n-    newnode.appendChild(newtext)\r\n-    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\r\n-    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode) \r\n-    \r\n-    \r\n-    # OS Architecture \r\n-    newnode = xmlFile.createElement(\"OSARCHITECTURE\")\r\n-    newtext = xmlFile.createTextNode(lastInformation['osArchitecture'])\r\n-    refnode = xmlFile.getElementsByTagName(\"OSNAME\")[0]\r\n-    \r\n-    newnode.appendChild(newtext)\r\n-    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\r\n-    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode) \r\n-\t\r\n-\t\r\n-    # Last login Date\r\n-    newnode = xmlFile.createElement(\"DATELASTLOGGEDUSER\")\r\n-    newtext = xmlFile.createTextNode(lastInformation['lastLogin'][1])\r\n-    refnode = xmlFile.getElementsByTagName(\"LASTLOGGEDUSER\")[0]\r\n-    \r\n-    newnode.appendChild(newtext)\r\n-    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\r\n-    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode)     \r\n-    \r\n-    \r\n-    # Default Gateway\r\n-    newnode = xmlFile.createElement(\"DEFAULTGATEWAY\")\r\n-    newtext = xmlFile.createTextNode(lastInformation['defaultGateway'])\r\n-    refnode = xmlFile.getElementsByTagName(\"HARDWARE\")[0]\r\n-    \r\n-    newnode.appendChild(newtext)\r\n-    refnode.appendChild(newnode)\r\n-    refnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-    \r\n-    \r\n-    # First boot date\r\n-    newnode = xmlFile.createElement(\"DATEFIRSTRUN\")\r\n-    newtext = xmlFile.createTextNode(lastInformation['dateFirst'])\r\n-    refnode = xmlFile.getElementsByTagName(\"BIOS\")[0]\r\n-    \r\n-    newnode.appendChild(newtext)\r\n-    refnode.appendChild(newnode)\r\n-    refnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-    \r\n-    \r\n-    # Last boot date\r\n-    newnode = xmlFile.createElement(\"DATELASTRUN\")\r\n-    newtext = xmlFile.createTextNode(lastInformation['dateLastBoot'])\r\n-    refnode = xmlFile.getElementsByTagName(\"BIOS\")[0]\r\n-    \r\n-    newnode.appendChild(newtext)\r\n-    refnode.appendChild(newnode)\r\n-    refnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-    \r\n-    # Who is Burner ?\r\n-    key = _winreg.OpenKey(_winreg.HKEY_CURRENT_USER,\"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\CD Burning\\Drives\")\r\n-    deviceKey = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"System\\MountedDevices\\\\\")\r\n-    #Search the tag of all burner\r\n-    burner = []\r\n-    try:\r\n-        i = 0\r\n-        while True:\r\n-            keyname = _winreg.EnumKey(key,i)\r\n-            subkey = _winreg.OpenKey(_winreg.HKEY_CURRENT_USER,\"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\CD Burning\\Drives\\\\\"+keyname)\r\n-            if not ( _winreg.QueryValueEx(subkey,\"Drive Type\")[0] == 3 ):\r\n-                burner.append( _winreg.QueryValueEx(deviceKey,\"\\\\??\\\\\"+keyname)[0] )\r\n-            \r\n-            _winreg.CloseKey(subkey)\r\n-            i = i + 1\r\n-    except WindowsError: # pyflakes.ignore\r\n-        pass    \r\n-    _winreg.CloseKey(key)\r\n-    \r\n-    #Add if the drive is burner\r\n-    for device in xmlFile.getElementsByTagName(\"DRIVES\"):\r\n-        if device.getElementsByTagName(\"TYPE\")[0].firstChild.nodeValue == \"CD-Rom Drive\" :\r\n-            isBurner = False\r\n-            newnode = xmlFile.createElement(\"BURNER\")\r\n-            i = 0\r\n-            while i < len(burner) and not isBurner :\r\n-                #Compare the tag with the tag of DosDevices to found the letter device of the burner\r\n-                isBurner = ( _winreg.QueryValueEx(deviceKey,\"\\\\DosDevices\\\\\"+ device.getElementsByTagName(\"LETTER\")[0].firstChild.nodeValue[0]+\":\")[0] == burner[i] )\r\n-                if isBurner :\r\n-                    del burner[i]\r\n-                i += 1  \r\n-            \r\n-            if isBurner:\r\n-                newtext = xmlFile.createTextNode( \"Burner\" )\r\n-            else:\r\n-                newtext = xmlFile.createTextNode( \"Only Reader\" )\r\n-            \r\n-            newnode.appendChild(newtext)\r\n-            device.appendChild(newnode)\r\n-            device.appendChild(xmlFile.createTextNode(\"\\n\"))        \r\n-    \r\n-    _winreg.CloseKey(deviceKey)  \r\n-    \r\n-    # Initializing Variable \r\n-    listSoftXML = xmlFile.getElementsByTagName(\"SOFTWARES\")\r\n-    listSoftXMLDefault = xmlFile.getElementsByTagName(\"SOFTWARES\")\r\n-    OSNAME = xmlFile.getElementsByTagName(\"OSNAME\")[0].firstChild.nodeValue\r\n-    defaultNode = listSoftXMLDefault[0].cloneNode(1)  \r\n-    key = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\")\r\n-    updateDetection = Pulse2InventoryProxyConfig().updatedetection\r\n-    \r\n-    try:\r\n-        i = 0\r\n-        while True:         #For every software in Uninstall Registry          \r\n-            keyname = _winreg.EnumKey(key,i)\r\n-            subkey = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\\\\"+keyname)\r\n-            \r\n-            try:\r\n-                displayName = _winreg.QueryValueEx(subkey,\"DisplayName\")[0]\r\n-                nodeId = foundNodeInList(listSoftXML,\"NAME\",displayName)                 \r\n-                                \r\n-                if nodeId != -1:\r\n-                    selectnode = listSoftXML[nodeId]\r\n-\t\t\t\t    #del(listSoftXML[nodeId])       # Warning : Both key Registry can be exist for the same software.\r\n-                                                    # Drop used software can acelerat the improving\r\n-                                                    # but it can lost some information in two places.\r\n-\t\t\t\t    #Type Package\r\n-                    newnode = xmlFile.createElement(\"FROM\")\r\n-                    newtext = xmlFile.createTextNode('win')\r\n-                    \r\n-                    newnode.appendChild(newtext)\r\n-                    selectnode.appendChild(newnode)\r\n-                    selectnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-\t\t\t\t\t\r\n-\t\t\t\t\t\r\n-                    #Software installation Date\r\n-                    try:\r\n-                        installDate = _winreg.QueryValueEx(subkey,\"InstallDate\")[0] \r\n-                        installDate = windowsDateConversion(installDate,False)                       \r\n-                    except WindowsError: # pyflakes.ignore\r\n-                        installDate = \"N/A\"\r\n-                    \r\n-                    newnode = xmlFile.createElement(\"INSTALLDATE\")\r\n-                    newtext = xmlFile.createTextNode(installDate)\r\n-                        \r\n-                    newnode.appendChild(newtext)\r\n-                    selectnode.appendChild(newnode)\r\n-                    selectnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-                                        \r\n-                    \r\n-                    # Version Check\r\n-                    try:\r\n-                        refnode = selectnode.getElementsByTagName(\"VERSION\")[0].firstChild\r\n-                        if refnode.nodeValue == \"N/A\":\r\n-                            displayversion = _winreg.QueryValueEx(subkey,\"DisplayVersion\")[0]\r\n-                            refnode.nodeValue = displayversion                      \r\n-                    except WindowsError: # pyflakes.ignore\r\n-                        pass                   \r\n-                    \r\n-                    # Software size calculated on hardDisk\r\n-                    try:\r\n-                        folder = _winreg.QueryValueEx(subkey,\"InstallLocation\")[0]\r\n-                        if len(folder) > 0 :\r\n-                            foldersize = sizeFolder(folder)\r\n-                            if not (foldersize > 0):\r\n-                                foldersize = \"N/A\"\r\n-                                \r\n-                        else:\r\n-                            foldersize = \"N/A\"\r\n-                            newnode = xmlFile.createElement(\"FOLDER\")\r\n-                            newtext = xmlFile.createTextNode(\"N/A\")\r\n-                            refnode = selectnode.getElementsByTagName(\"VERSION\")[0]\r\n-                            \r\n-                            newnode.appendChild(newtext)\r\n-                            refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\r\n-                            newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode)\r\n-                                                \r\n-                    except WindowsError: # pyflakes.ignore\r\n-                        foldersize = \"N/A\"\r\n-                        folder = \"N/A\"\r\n-                        \r\n-                    newnode = xmlFile.createElement(\"FOLDERSIZE\")\r\n-                    newtext = xmlFile.createTextNode(str(foldersize))\r\n-                    refnode = selectnode.getElementsByTagName(\"FOLDER\")[0]\r\n-        \r\n-                    newnode.appendChild(newtext)\r\n-                    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\r\n-                    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode)  \r\n-                    \r\n-                    # Software Size estimated by Operating System\r\n-                    try:\r\n-                        estimatedSize = _winreg.QueryValueEx(subkey,\"EstimatedSize\")[0]\r\n-                        if not (estimatedSize > 0):\r\n-                            estimatedSize = \"N/A\"\r\n-                    except WindowsError: # pyflakes.ignore\r\n-                        estimatedSize = \"N/A\"\r\n-                    \r\n-                    selectnode.getElementsByTagName(\"FILESIZE\")[0].firstChild.nodeValue = estimatedSize\r\n-                    \r\n-                    #Uninstall command\r\n-                    try:\r\n-                        uninstallCommand = _winreg.QueryValueEx(subkey,\"UninstallString\")[0]\r\n-                    except WindowsError: # pyflakes.ignore\r\n-                        uninstallCommand = \"N/A\"\r\n-                    \r\n-                    if len(uninstallCommand)==0:\r\n-                        uninstallCommand = \"N/A\"\r\n-                    \r\n-                    newnode = xmlFile.createElement(\"UNINSTALL\")\r\n-                    newtext = xmlFile.createTextNode(uninstallCommand)\r\n-        \r\n-                    newnode.appendChild(newtext)\r\n-                    selectnode.appendChild(newnode)\r\n-                    selectnode.appendChild(xmlFile.createTextNode(\"\\n\"))            \r\n-                    \r\n-                    # update detections\r\n-                    isUpdate = False\r\n-                    if updateDetection:\r\n-                        try:\r\n-                            parentKey = _winreg.QueryValueEx(subkey,\"ParentKeyName\")[0]\r\n-                            isUpdate = True\r\n-                            nodeParentId = -1\r\n-                            if len(parentKey)>0:\r\n-                                if parentKey =='OperatingSystem' :  #Update de l'OS\r\n-                                    nodeParentId = foundNodeInList(listSoftXMLDefault,\"NAME\",OSNAME)\r\n-                                    parentName = OSNAME\r\n-                                else :\r\n-                                    try:\r\n-                                        parentRegisterKey = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\\\\"+parentKey)\r\n-                                        parentName = _winreg.QueryValueEx(parentRegisterKey,\"DisplayName\")[0]\r\n-                                        _winreg.CloseKey(parentRegisterKey)\r\n-                                        nodeParentId = foundNodeInList(listSoftXMLDefault,\"NAME\",parentName)\r\n-                                    except WindowsError:    # if parent doesn't exist # pyflakes.ignore\r\n-                                        parentName = _winreg.QueryValueEx(subkey,\"ParentDisplayName\")[0]\r\n-                                        if len(parentName)>0:   # search parent with his name\r\n-                                            nodeParentId = foundNodeInList(listSoftXMLDefault,\"NAME\",parentName)\r\n-                                            if nodeParentId == -1:  # create the simulated parent\r\n-                                                newnode = defaultNode.cloneNode(1)\r\n-                                                nodeslist = newnode.childNodes\r\n-                                                for j in range(0,len(nodeslist)):\r\n-                                                    if j%2==1:\r\n-                                                        nodeslist[j].firstChild.nodeValue = \"N/A\"\r\n-                                                        \r\n-                                                newnode.getElementsByTagName(\"NAME\")[0].firstChild.nodeValue = parentName\r\n-                                                xmlFile.getElementsByTagName(\"CONTENT\")[0].insertBefore(newnode,listSoftXMLDefault[len(listSoftXMLDefault)-1])\r\n-                                                nodeParentId = foundNodeInList(listSoftXMLDefault,\"NAME\",parentName)\r\n-                                            \r\n-                                            listSoftXMLDefault = xmlFile.getElementsByTagName(\"SOFTWARES\")\r\n-                                            nodeParentId = foundNodeInList(listSoftXMLDefault,\"NAME\",parentName)\r\n-                                \r\n-                                if nodeParentId > -1:\r\n-                                    '''\r\n-                                    selectnode.tagName = \"UPDATE\"                       #to transformed the select node (update) \r\n-                                    del(listSoftXML[nodeId])                            #on child of his parent node (software updated)\r\n-                                    selectnode.parentNode.removeChild(selectnode.previousSibling)\r\n-                                    listSoftXMLDefault[nodeParentId].appendChild(selectnode)\r\n-                                    listSoftXMLDefault[nodeParentId].appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-                                    '''\r\n-                                    \r\n-                                    selectnode.setAttribute(\"parent\",parentName)    #only notified the dependance by attribute\r\n-                                    del(listSoftXML[nodeId])\r\n-                                      \r\n-                        except WindowsError: # pyflakes.ignore\r\n-                            isUpdate = False\r\n-                    \r\n-                    # if not update, we calculate this Rate Of Use and get icon\r\n-                    #log-on frequency    Only for WinXP et 2K (On Vista, it's doesn't exist)\r\n-                    if not updateDetection or ( updateDetection and not isUpdate ):\r\n-                        try:\r\n-                            arpKey = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\App Management\\ARPCache\\\\\"+keyname)\r\n-                            try:\r\n-                                rateOfUse = _winreg.QueryValueEx(arpKey,\"SlowInfoCache\")[0]\r\n-                                valueRateOfUse = ord(rateOfUse[24])\r\n-                                if valueRateOfUse == 255:\r\n-                                    valueRateOfUse = \"N/A\"\r\n-                                    \r\n-                            except WindowsError: # pyflakes.ignore\r\n-                                valueRateOfUse = \"N/A\"\r\n-                                \r\n-                            _winreg.CloseKey(arpKey)\r\n-                        except WindowsError: # pyflakes.ignore\r\n-                            valueRateOfUse = \"N/A\"\r\n-                            \r\n-                        refnode = selectnode.getElementsByTagName(\"RATEOFUSE\") \r\n-                        if len(refnode) == 0:\r\n-                            newnode = xmlFile.createElement(\"RATEOFUSE\")\r\n-                            newtext = xmlFile.createTextNode(str(valueRateOfUse))\r\n-                                \r\n-                            newnode.appendChild(newtext)\r\n-                            selectnode.appendChild(newnode)\r\n-                            selectnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-                        else :\r\n-                            if valueRateOfUse != \"N/A\":\r\n-                                if refnode[0].firstChild.valueNode != \"N/A\":\r\n-                                    refnode[0].firstChild.valueNode = refnode[0].firstChild.valueNode + valueRateOfUse\r\n-                                else :\r\n-                                    refnode[0].firstChild.valueNode = valueRateOfUse\r\n-                        \r\n-                        \r\n-                        if Pulse2InventoryProxyConfig().addicon:\r\n-                            try:\r\n-                                iconpath = _winreg.QueryValueEx(subkey,\"DisplayIcon\")[0]\r\n-                                if iconpath[0] == '\"':\r\n-                                    iconpath = iconpath[1:len(iconpath)-1]\r\n-                                \r\n-                                k = len(iconpath) -1    \r\n-                                while ( k > (len(iconpath) - 4) and iconpath[k] != ',' ):\r\n-                                    k -= 1\r\n-                                \r\n-                                nIcon = 0\r\n-                                if iconpath[k] == ',':\r\n-                                    try:    \r\n-                                        if (k < len(iconpath)):\r\n-                                            nIcon = int(iconpath[k+1])\r\n-                                    except ValueError :\r\n-                                        pass\r\n-                                    iconpath = iconpath[0:k] \r\n-                                length = len(iconpath)\r\n-                                \r\n-                                if iconpath[length-3:] == 'ico':\r\n-                                    stringBit = windowsIconGetter(iconpath, nIcon, False)\r\n-                                else:\r\n-                                    stringBit = windowsIconGetter(iconpath, nIcon, True )\r\n-                                \r\n-                                if stringBit != None:\r\n-                                    newnode = xmlFile.createElement(\"ICON\")\r\n-                                    newtext = xmlFile.createTextNode( stringBit )\r\n-                        \r\n-                                    newnode.appendChild(newtext)\r\n-                                    selectnode.appendChild(newnode)\r\n-                                    selectnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-                                \r\n-                            except WindowsError: # pyflakes.ignore\r\n-                                pass\r\n-                                \r\n-            except WindowsError: # pyflakes.ignore\r\n-                pass\r\n-            \r\n-            _winreg.CloseKey(subkey)\r\n-            i += 1\r\n-            \r\n-    except WindowsError: # pyflakes.ignore\r\n-        pass\r\n-\r\n-    if Pulse2InventoryProxyConfig().addicon:\r\n-        # Do NOT FORGET !\r\n-        os.remove(dirTmpFile)\r\n-        \r\n-    _winreg.CloseKey(key)\r\n-    xmlString = xmlFile.toxml(\"utf-8\")\r\n-    return xmlString\r\n-\r\n-'''\r\n-Search in the list of xml node, the value in tagName\r\n-@param listnode: the list of node\r\n-@param tagName: the Tag Name to procedd reasearch\r\n-@param value: the value research\r\n-@return: the index in the list of the node, else -1\r\n-'''\r\n-def foundNodeInList (listnode, tagName, value):\r\n-    \r\n-    i = 0\r\n-    found = False\r\n-    \r\n-    while not found and len(listnode)>i:               \r\n-        found = ( listnode[i].getElementsByTagName(tagName)[0].firstChild.nodeValue == value )\r\n-        i += 1        \r\n-        \r\n-    if found:\r\n-        i -= 1\r\n-    else:\r\n-        i = -1\r\n-                \r\n-    return i\r\n-\r\n-'''\r\n-Improve the xml File and eventuality, save it on local machine\r\n-@param xmlFileString: the xml String to improve\r\n-@return: the improving xml String\r\n-'''\r\n-def improveXML( xmlFileString ):\r\n-        \r\n-    xmlFileString = xmlUpdate(xmlFileString, informationSearch() )\r\n-    if Pulse2InventoryProxyConfig().savexmlmodified:\r\n-        filout = open('XmlOutput.xml','w')\r\n-        for i in xmlFileString:\r\n-            filout.write(i)    \r\n-        filout.close()\r\n-          \r\n-    return xmlFileString\r\n-\r\n-'''\r\n-Add the last log of OCS in xml\r\n-@param xmlString: the xml String to modify\r\n-@return: the xml String with the log\r\n-'''\r\n-def getOcsDebugLog( xmlString ):\r\n-    \r\n-    xmlFile = xml.dom.minidom.parseString(xmlString)\r\n-    userDomaine = xmlFile.getElementsByTagName(\"USERDOMAIN\")[0].firstChild.nodeValue\r\n-    ocsFolder = Pulse2InventoryProxyConfig().command_name\r\n-    i = len(ocsFolder)\r\n-    found = False\r\n-    while not found and i>0:\r\n-        found = ( ocsFolder[i-1] == '\\\\' )\r\n-        i -= 1 \r\n-    \r\n-    if found :\r\n-        logFile = open ( ocsFolder[0:i+1] + userDomaine + \".log\" , \"r\")\r\n-        logFileString = logFile.read()\r\n-        logFile.close()\r\n-    else :\r\n-        logFileString = \"Error : couldn't open Log File\"\r\n-        \r\n-    newnode = xmlFile.createElement(\"OCSDEBUG\")\r\n-    newsubnode = xmlFile.createElement(\"DEBUGLOG\")\r\n-    newtext = xmlFile.createTextNode(logFileString)\r\n-    refnode = xmlFile.getElementsByTagName(\"CONTENT\")[0]\r\n-    #Optional : help to the final xml File can be esay read\r\n-    newsubnode.appendChild(newtext)\r\n-    newnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-    newnode.appendChild(newsubnode)\r\n-    newnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-    refnode.appendChild(newnode)\r\n-    refnode.appendChild(xmlFile.createTextNode(\"\\n\"))\r\n-    \r\n-    xmlString = xmlFile.toxml(\"utf-8\")  \r\n-    return xmlString\r\n+#!/usr/bin/python\n+# -*- coding: utf-8; -*-\n+#\n+# (c) 2007-2009 Mandriva, http://www.mandriva.com/\n+#\n+# $Id: improve.py 90 2008-04-8 09:24:56Z neisen $\n+#\n+# This file is part of Pulse 2, http://pulse2.mandriva.org\n+#\n+# Pulse 2 is free software; you can redistribute it and/or modify\n+# it under the terms of the GNU General Public License as published by\n+# the Free Software Foundation; either version 2 of the License, or\n+# (at your option) any later version.\n+#\n+# Pulse 2 is distributed in the hope that it will be useful,\n+# but WITHOUT ANY WARRANTY; without even the implied warranty of\n+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n+# GNU General Public License for more details.\n+#\n+# You should have received a copy of the GNU General Public License\n+# along with Pulse 2; if not, write to the Free Software\n+# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,\n+# MA 02110-1301, USA.\n+\n+'''\n+This is the module to add information to OCS XML\n+for the Windows platforms\n+'''\n+\n+import wmi\n+import _winreg\n+import os\n+import xml.dom.minidom\n+\n+from pulse2.proxyssl.config import Pulse2InventoryProxyConfig\n+\n+if Pulse2InventoryProxyConfig().addicon:\n+    import win32ui\n+    import win32gui\n+    import win32con\n+    import win32api\n+    import cStringIO\n+    import Image    # need install PIL package http://www.pythonware.com/products/pil/\n+    import base64\n+    import tempfile\n+    \n+    #system icon size \n+    ico_x = win32api.GetSystemMetrics(win32con.SM_CXICON)\n+    \n+    #tempory file\n+    tmpfile = tempfile.mkstemp()\n+    dirTmpFile = tmpfile[1] \n+    #close the opened temp file (SaveBitmapFile Error)   \n+    file = os.fdopen(tmpfile[0])\n+    file.close()\n+\n+'''    \n+Get the icon of file\n+@param path: the path of the file\n+@param nIcon: position of the icon in the file\n+@param exeOrDll=True: set False if is a icon file \n+@return string bit of icon in Jpeg Format encoded in base64, else Error : None\n+'''    \n+def windowsIconGetter(path, nIcon = 0 , exeOrDll = True):  #It's can be exe, dll, or already ico\n+    \n+    if os.path.isfile(path):\n+        dst = cStringIO.StringIO()\n+        if exeOrDll:\n+            large, small = win32gui.ExtractIconEx(path,nIcon)\n+            win32gui.DestroyIcon(small[0])\n+            #creating a destination memory DC \n+            hdc = win32ui.CreateDCFromHandle( win32gui.GetDC(0) )\n+            hbmp = win32ui.CreateBitmap()\n+            hbmp.CreateCompatibleBitmap(hdc, ico_x, ico_x)\n+            hdc = hdc.CreateCompatibleDC()\n+            hdc.SelectObject( hbmp )\n+            #set the background in white\n+            hdc.FillSolidRect( (0,0,ico_x,ico_x), 0xffffff )\n+            #draw a icon in it\n+            hdc.DrawIcon( (0,0), large[0] )\n+            win32gui.DestroyIcon(large[0])\n+            #convert picture in JPEG\n+            hbmp.SaveBitmapFile( hdc, dirTmpFile)\n+            im = Image.open(dirTmpFile)\n+        else:\n+            im = Image.open(path)\n+        \n+        try:\n+            im.save(dst, \"JPEG\")\n+        except IOError:\n+            return None\n+                \n+        dst.seek(0)\n+        return base64.b64encode( dst.read() )   \n+    \n+    else:    \n+        return None \n+ \n+'''\n+Convert the Registry Date in Humain format date DD/MM/YYYY HH:MM:SS\n+@param date: date in registry format to convert\n+@param displayHour=True: if the registry date have no reached hour, set False to doesn't get 00:00:00\n+@return: convert date\n+'''\n+def windowsDateConversion(date, displayHour = True):\n+\n+    if (len(date)==8 or len(date)==25):     # check if it's good windows date system\n+        finaldate = date[6:8]+\"/\"+date[4:6]+\"/\"+date[0:4]\n+        if displayHour:\n+            finaldate = finaldate +\" \"+date[8:10]+\":\"+date[10:12]+\":\"+date[12:14]\n+    else:   # if the date is not in registry format\n+        finaldate = date\n+    \n+    return finaldate\n+\n+'''\n+Calculate the size of folder\n+@param folder: the path of the folder to calculate\n+@return: the size of the folder in Ko \n+'''\n+def sizeFolder(folder):\n+    size = 0\n+    for (current, subFolder, files) in os.walk(folder):\n+        size = size + sum( os.path.getsize( os.path.join(current, file) ) for file in files )\n+    return size/1024 #Ko\n+\n+'''\n+Search the information to add\n+@return: Dictonary with information asked\n+'''\n+def informationSearch():            # Found any information for the computer.\n+    result = {}                     # Software infomration will be reached in next time\n+    \n+    #With WMI\n+    wmiObject = wmi.WMI()\n+    \n+    #Company Register\n+    try:\n+        companyRegister = wmiObject.Win32_OperatingSystem([\"Organization\"])[0].Organization\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        companyRegister = \"N/A\"\n+        \n+    result['companyRegister']=companyRegister\n+    \n+    #Os Architecture (32-64 bit) only for Vista and superior\n+    try:\n+        osArchitecture = wmiObject.Win32_OperatingSystem([\"OSArchitecture\"])[0].OSArchitecture\n+    except WindowsError: # pyflakes.ignore\n+        osArchitecture = \"N/A\"\n+    except wmi.x_wmi :    # If os is XP, 2003, 2000, 98, 95, ...\n+        osArchitecture = \"32-bit\"\n+        \n+    result['osArchitecture']=osArchitecture\n+    \n+    # First boot\n+    try:\n+        dateFirst = wmiObject.Win32_BIOS([\"ReleaseDate\"])[0].ReleaseDate\n+        dateFirst = windowsDateConversion(dateFirst,False)\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        dateFirst = \"N/A\"\n+        \n+    result['dateFirst']=dateFirst\n+    \n+    # Last boot\n+    try:    \n+        dateLastBoot = wmiObject.Win32_OperatingSystem([\"LastBootUpTime\"])[0].LastBootUpTime\n+        dateLastBoot = windowsDateConversion(dateLastBoot)\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        dateLastBoot = \"N/A\"\n+        \n+    result['dateLastBoot'] = dateLastBoot\n+    \n+    # Serial Number\n+    try:  \n+        serialNumber = wmiObject.Win32_BIOS([\"SerialNumber\"])[0].SerialNumber\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        serialNumber = \"N/A\"\n+           \n+    result['serialNumber'] = serialNumber\n+    \n+    # Operating system installation date\n+    try:    \n+        dateInstall = wmiObject.Win32_OperatingSystem([\"InstallDate\"])[0].InstallDate\n+        dateInstall = windowsDateConversion(dateInstall)\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        dateInstall = \"N/A\"\n+        \n+    result['installDate'] = dateInstall\n+    \n+    # Default Gateway\n+    try:    \n+        interfacesAdapter = wmiObject.Win32_NetworkAdapterConfiguration([\"DefaultIPGateway\"])\n+        for interface in interfacesAdapter:\n+            if not (interface.DefaultIPGateway is None):\n+                defaultGateway = interface.DefaultIPGateway[0]\n+                break\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        defaultGateway = \"N/A\"\n+        \n+    result['defaultGateway'] = defaultGateway\n+        \n+        \n+    # Operating system folder\n+    try:\n+        # os.getenv(\"windir\")\n+        result['OSfolder'] = wmiObject.Win32_OperatingSystem([\"WindowsDirectory\"])[0].WindowsDirectory     #by WMI. The installation can be anywhere\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        result['OSfolder'] = \"N/A\"    \n+        \n+    # last login date\n+    wmiObject = wmi.WMI(privileges=[\"Security\"])\n+    try:\n+        lastLoginLog = wmiObject.Win32_NTLogEvent([\"InsertionStrings\",\"TimeGenerated\"],EventCode=680)[0]    # For Win XP et 2k, EventCode = 680, but with Vista EventCode = 4624\n+        lastLogin = [lastLoginLog.InsertionStrings[1],lastLoginLog.TimeGenerated]\n+        # convert the date\n+        lastLogin[1] = windowsDateConversion(lastLogin[1])\n+        result['lastLogin']=lastLogin\n+    except (WindowsError, wmi.x_wmi, IndexError): # pyflakes.ignore\n+        result['lastLogin']=[\"N/A\",\"N/A\"]\n+    \n+    return result\n+    \n+'''\n+Improve the xml File with the Information and another research\n+@param xmlString: the xml String of the xml file to improve\n+@param lastInformation: some information to add in xml\n+@return: the improving xmlString \n+'''\n+def xmlUpdate(xmlString, lastInformation):\n+    \n+    xmlFile = xml.dom.minidom.parseString(xmlString)\n+    \n+    # Check Serial number between Ocs and WMI\n+    ssn = xmlFile.getElementsByTagName(\"SSN\")[0].childNodes[0].nodeValue\n+    if ( len(lastInformation['serialNumber']) > 0 and ssn != lastInformation['serialNumber'] ):\n+        ssn = lastInformation['serialNumber']\n+        \n+    # Operating system installation date\n+    newnode = xmlFile.createElement(\"INSTALLDATE\")\n+    newtext = xmlFile.createTextNode(lastInformation['installDate'])\n+    refnode = xmlFile.getElementsByTagName(\"OSVERSION\")[0]\n+    \n+    newnode.appendChild(newtext)\n+    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\n+    #Optionnal : help to the final xml File can be easy read\n+    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode)    \n+    \n+    \n+    # Company Register\n+    newnode = xmlFile.createElement(\"WINCOMPANY\")\n+    newtext = xmlFile.createTextNode(lastInformation['companyRegister'])\n+    refnode = xmlFile.getElementsByTagName(\"WINOWNER\")[0]\n+    \n+    newnode.appendChild(newtext)\n+    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\n+    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode) \n+    \n+    \n+    # OS Architecture \n+    newnode = xmlFile.createElement(\"OSARCHITECTURE\")\n+    newtext = xmlFile.createTextNode(lastInformation['osArchitecture'])\n+    refnode = xmlFile.getElementsByTagName(\"OSNAME\")[0]\n+    \n+    newnode.appendChild(newtext)\n+    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\n+    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode) \n+\t\n+\t\n+    # Last login Date\n+    newnode = xmlFile.createElement(\"DATELASTLOGGEDUSER\")\n+    newtext = xmlFile.createTextNode(lastInformation['lastLogin'][1])\n+    refnode = xmlFile.getElementsByTagName(\"LASTLOGGEDUSER\")[0]\n+    \n+    newnode.appendChild(newtext)\n+    refnode.parentNode.insertBefore(newnode,refnode.nextSibling)\n+    newnode.parentNode.insertBefore(xmlFile.createTextNode(\"\\n\"),newnode)     \n+    \n+    \n+    # Default Gateway\n+    newnode = xmlFile.createElement(\"DEFAULTGATEWAY\")\n+    newtext = xmlFile.createTextNode(lastInformation['defaultGateway'])\n+    refnode = xmlFile.getElementsByTagName(\"HARDWARE\")[0]\n+    \n+    newnode.appendChild(newtext)\n+    refnode.appendChild(newnode)\n+    refnode.appendChild(xmlFile.createTextNode(\"\\n\"))\n+    \n+    \n+    # First boot date\n+    newnode = xmlFile.createElement(\"DATEFIRSTRUN\")\n+    newtext = xmlFile.createTextNode(lastInformation['dateFirst'])\n+    refnode = xmlFile.getElementsByTagName(\"BIOS\")[0]\n+    \n+    newnode.appendChild(newtext)\n+    refnode.appendChild(newnode)\n+    refnode.appendChild(xmlFile.createTextNode(\"\\n\"))\n+    \n+    \n+    # Last boot date\n+    newnode = xmlFile.createElement(\"DATELASTRUN\")\n+    newtext = xmlFile.createTextNode(lastInformation['dateLastBoot'])\n+    refnode = xmlFile.getElementsByTagName(\"BIOS\")[0]\n+    \n+    newnode.appendChild(newtext)\n+    refnode.appendChild(newnode)\n+    refnode.appendChild(xmlFile.createTextNode(\"\\n\"))\n+    \n+    # Who is Burner ?\n+    key = _winreg.OpenKey(_winreg.HKEY_CURRENT_USER,\"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\CD Burning\\Drives\")\n+    deviceKey = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"System\\MountedDevices\\\\\")\n+    #Search the tag of all burner\n+    burner = []\n+    try:\n+        i = 0\n+        while True:\n+            keyname = _winreg.EnumKey(key,i)\n+            subkey = _winreg.OpenKey(_winreg.HKEY_CURRENT_USER,\"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\CD Burning\\Drives\\\\\"+keyname)\n+            if not ( _winreg.QueryValueEx(subkey,\"Drive Type\")[0] == 3 ):\n+                burner.append( _winreg.QueryValueEx(deviceKey,\"\\\\??\\\\\"+keyname)[0] )\n+            \n+            _winreg.CloseKey(subkey)\n+            i = i + 1\n+    except WindowsError: # pyflakes.ignore\n+        pass    \n+    _winreg.CloseKey(key)\n+    \n+    #Add if the drive is burner\n+    for device in xmlFile.getElementsByTagName(\"DRIVES\"):\n+        if device.getElementsByTagName(\"TYPE\")[0].firstChild.nodeValue == \"CD-Rom Drive\" :\n+            isBurner = False\n+            newnode = xmlFile.createElement(\"BURNER\")\n+            i = 0\n+            while i < len(burner) and not isBurner :\n+                #Compare the tag with the tag of DosDevices to found the letter device of the burner\n+                isBurner = ( _winreg.QueryValueEx(deviceKey,\"\\\\DosDevices\\\\\"+ device.getElementsByTagName(\"LETTER\")[0].firstChild.nodeValue[0]+\":\")[0] == burner[i] )\n+                if isBurner :\n+                    del burner[i]\n+                i += 1  \n+            \n+            if isBurner:\n+                newtext = xmlFile.createTextNode( \"Burner\" )\n+            else:\n+                newtext = xmlFile.createTextNode( \"Only Reader\" )\n+            \n+            newnode.appendChild(newtext)\n+            device.appendChild(newnode)\n+            device.appendChild(xmlFile.createTextNode(\"\\n\"))        \n+    \n+    _winreg.CloseKey(deviceKey)  \n+    \n+    # Initializing Variable \n+    listSoftXML = xmlFile.getElementsByTagName(\"SOFTWARES\")\n+    listSoftXMLDefault = xmlFile.getElementsByTagName(\"SOFTWARES\")\n+    OSNAME = xmlFile.getElementsByTagName(\"OSNAME\")[0].firstChild.nodeValue\n+    defaultNode = listSoftXMLDefault[0].cloneNode(1)  \n+    key = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\")\n+    updateDetection = Pulse2InventoryProxyConfig().updatedetection\n+    \n+    try:\n+        i = 0\n+        while True:         #For every software in Uninstall Registry          \n+            keyname = _winreg.EnumKey(key,i)\n+            subkey = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE,\"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\\\\"+keyname)","path":"pulse2/services/pulse2/proxyssl/improveWin.py","position":1038,"original_position":1038,"commit_id":"a129f05ea8374422091d8dff0c7c42455643dcd0","original_commit_id":"a129f05ea8374422091d8dff0c7c42455643dcd0","user":{"login":"neoclust","id":285923,"avatar_url":"https://avatars.githubusercontent.com/u/285923?v=3","gravatar_id":"","url":"https://api.github.com/users/neoclust","html_url":"https://github.com/neoclust","followers_url":"https://api.github.com/users/neoclust/followers","following_url":"https://api.github.com/users/neoclust/following{/other_user}","gists_url":"https://api.github.com/users/neoclust/gists{/gist_id}","starred_url":"https://api.github.com/users/neoclust/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/neoclust/subscriptions","organizations_url":"https://api.github.com/users/neoclust/orgs","repos_url":"https://api.github.com/users/neoclust/repos","events_url":"https://api.github.com/users/neoclust/events{/privacy}","received_events_url":"https://api.github.com/users/neoclust/received_events","type":"User","site_admin":false},"body":"__[flake8]__\n* [E231] missing whitespace after ','\n* [E501] line too long (128 > 79 characters)","created_at":"2016-06-01T13:30:06Z","updated_at":"2016-06-01T13:30:06Z","html_url":"https://github.com/neoclust/pulse/pull/6#discussion_r65359442","pull_request_url":"https://api.github.com/repos/neoclust/pulse/pulls/6","_links":{"self":{"href":"https://api.github.com/repos/neoclust/pulse/pulls/comments/65359442"},"html":{"href":"https://github.com/neoclust/pulse/pull/6#discussion_r65359442"},"pull_request":{"href":"https://api.github.com/repos/neoclust/pulse/pulls/6"}}},"pull_request":{"url":"https://api.github.com/repos/neoclust/pulse/pulls/6","id":72175646,"html_url":"https://github.com/neoclust/pulse/pull/6","diff_url":"https://github.com/neoclust/pulse/pull/6.diff","patch_url":"https://github.com/neoclust/pulse/pull/6.patch","issue_url":"https://api.github.com/repos/neoclust/pulse/issues/6","number":6,"state":"open","locked":false,"title":"Fix \"Use `is` or `is not` to compare with `None`\" issue","user":{"login":"neoclust","id":285923,"avatar_url":"https://avatars.githubusercontent.com/u/285923?v=3","gravatar_id":"","url":"https://api.github.com/users/neoclust","html_url":"https://github.com/neoclust","followers_url":"https://api.github.com/users/neoclust/followers","following_url":"https://api.github.com/users/neoclust/following{/other_user}","gists_url":"https://api.github.com/users/neoclust/gists{/gist_id}","starred_url":"https://api.github.com/users/neoclust/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/neoclust/subscriptions","organizations_url":"https://api.github.com/users/neoclust/orgs","repos_url":"https://api.github.com/users/neoclust/repos","events_url":"https://api.github.com/users/neoclust/events{/privacy}","received_events_url":"https://api.github.com/users/neoclust/received_events","type":"User","site_admin":false},"body":"This pull request automatically fixes all occurrences of the following issue:\n\nIssue type: [Use `is` or `is not` to compare with `None`](https://www.quantifiedcode.com/app/issue_class/3IY8CZ0v)\nIssue details: [https://www.quantifiedcode.com/app/project/gh:neoclust:pulse?groups=code_patterns/%3A3IY8CZ0v](https://www.quantifiedcode.com/app/project/gh:neoclust:pulse?groups=code_patterns/%3A3IY8CZ0v)\n\nTo adjust the commit message or the actual code changes, just [rebase](https://git-scm.com/docs/git-rebase) or [cherry-pick](https://git-scm.com/docs/git-cherry-pick) the commits.\nFor questions or feedback reach out to cody@quantifiedcode.com.\n\nLegal note: We won't claim any copyrights on the code changes.\n\nCheers,\n[Cody - Your code quality bot](https://www.quantifiedcode.com/cody)","created_at":"2016-06-01T12:57:41Z","updated_at":"2016-06-01T13:30:06Z","closed_at":null,"merged_at":null,"merge_commit_sha":"d00e01e854bf091b0f7df235725ff9a4b24c3112","assignee":null,"milestone":null,"commits_url":"https://api.github.com/repos/neoclust/pulse/pulls/6/commits","review_comments_url":"https://api.github.com/repos/neoclust/pulse/pulls/6/comments","review_comment_url":"https://api.github.com/repos/neoclust/pulse/pulls/comments{/number}","comments_url":"https://api.github.com/repos/neoclust/pulse/issues/6/comments","statuses_url":"https://api.github.com/repos/neoclust/pulse/statuses/a129f05ea8374422091d8dff0c7c42455643dcd0","head":{"label":"neoclust:autofix/wrapped2_to3_fix-4","ref":"autofix/wrapped2_to3_fix-4","sha":"a129f05ea8374422091d8dff0c7c42455643dcd0","user":{"login":"neoclust","id":285923,"avatar_url":"https://avatars.githubusercontent.com/u/285923?v=3","gravatar_id":"","url":"https://api.github.com/users/neoclust","html_url":"https://github.com/neoclust","followers_url":"https://api.github.com/users/neoclust/followers","following_url":"https://api.github.com/users/neoclust/following{/other_user}","gists_url":"https://api.github.com/users/neoclust/gists{/gist_id}","starred_url":"https://api.github.com/users/neoclust/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/neoclust/subscriptions","organizations_url":"https://api.github.com/users/neoclust/orgs","repos_url":"https://api.github.com/users/neoclust/repos","events_url":"https://api.github.com/users/neoclust/events{/privacy}","received_events_url":"https://api.github.com/users/neoclust/received_events","type":"User","site_admin":false},"repo":{"id":59030449,"name":"pulse","full_name":"neoclust/pulse","owner":{"login":"neoclust","id":285923,"avatar_url":"https://avatars.githubusercontent.com/u/285923?v=3","gravatar_id":"","url":"https://api.github.com/users/neoclust","html_url":"https://github.com/neoclust","followers_url":"https://api.github.com/users/neoclust/followers","following_url":"https://api.github.com/users/neoclust/following{/other_user}","gists_url":"https://api.github.com/users/neoclust/gists{/gist_id}","starred_url":"https://api.github.com/users/neoclust/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/neoclust/subscriptions","organizations_url":"https://api.github.com/users/neoclust/orgs","repos_url":"https://api.github.com/users/neoclust/repos","events_url":"https://api.github.com/users/neoclust/events{/privacy}","received_events_url":"https://api.github.com/users/neoclust/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/neoclust/pulse","description":"Management Console","fork":true,"url":"https://api.github.com/repos/neoclust/pulse","forks_url":"https://api.github.com/repos/neoclust/pulse/forks","keys_url":"https://api.github.com/repos/neoclust/pulse/keys{/key_id}","collaborators_url":"https://api.github.com/repos/neoclust/pulse/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/neoclust/pulse/teams","hooks_url":"https://api.github.com/repos/neoclust/pulse/hooks","issue_events_url":"https://api.github.com/repos/neoclust/pulse/issues/events{/number}","events_url":"https://api.github.com/repos/neoclust/pulse/events","assignees_url":"https://api.github.com/repos/neoclust/pulse/assignees{/user}","branches_url":"https://api.github.com/repos/neoclust/pulse/branches{/branch}","tags_url":"https://api.github.com/repos/neoclust/pulse/tags","blobs_url":"https://api.github.com/repos/neoclust/pulse/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/neoclust/pulse/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/neoclust/pulse/git/refs{/sha}","trees_url":"https://api.github.com/repos/neoclust/pulse/git/trees{/sha}","statuses_url":"https://api.github.com/repos/neoclust/pulse/statuses/{sha}","languages_url":"https://api.github.com/repos/neoclust/pulse/languages","stargazers_url":"https://api.github.com/repos/neoclust/pulse/stargazers","contributors_url":"https://api.github.com/repos/neoclust/pulse/contributors","subscribers_url":"https://api.github.com/repos/neoclust/pulse/subscribers","subscription_url":"https://api.github.com/repos/neoclust/pulse/subscription","commits_url":"https://api.github.com/repos/neoclust/pulse/commits{/sha}","git_commits_url":"https://api.github.com/repos/neoclust/pulse/git/commits{/sha}","comments_url":"https://api.github.com/repos/neoclust/pulse/comments{/number}","issue_comment_url":"https://api.github.com/repos/neoclust/pulse/issues/comments{/number}","contents_url":"https://api.github.com/repos/neoclust/pulse/contents/{+path}","compare_url":"https://api.github.com/repos/neoclust/pulse/compare/{base}...{head}","merges_url":"https://api.github.com/repos/neoclust/pulse/merges","archive_url":"https://api.github.com/repos/neoclust/pulse/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/neoclust/pulse/downloads","issues_url":"https://api.github.com/repos/neoclust/pulse/issues{/number}","pulls_url":"https://api.github.com/repos/neoclust/pulse/pulls{/number}","milestones_url":"https://api.github.com/repos/neoclust/pulse/milestones{/number}","notifications_url":"https://api.github.com/repos/neoclust/pulse/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/neoclust/pulse/labels{/name}","releases_url":"https://api.github.com/repos/neoclust/pulse/releases{/id}","deployments_url":"https://api.github.com/repos/neoclust/pulse/deployments","created_at":"2016-05-17T14:36:08Z","updated_at":"2016-05-17T14:36:18Z","pushed_at":"2016-06-01T12:57:42Z","git_url":"git://github.com/neoclust/pulse.git","ssh_url":"git@github.com:neoclust/pulse.git","clone_url":"https://github.com/neoclust/pulse.git","svn_url":"https://github.com/neoclust/pulse","homepage":"","size":144771,"stargazers_count":0,"watchers_count":0,"language":"Python","has_issues":false,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":6,"forks":0,"open_issues":6,"watchers":0,"default_branch":"master"}},"base":{"label":"neoclust:master","ref":"master","sha":"ac33dc4f917bb0b4fe59e9eeee6bd86c41b850b0","user":{"login":"neoclust","id":285923,"avatar_url":"https://avatars.githubusercontent.com/u/285923?v=3","gravatar_id":"","url":"https://api.github.com/users/neoclust","html_url":"https://github.com/neoclust","followers_url":"https://api.github.com/users/neoclust/followers","following_url":"https://api.github.com/users/neoclust/following{/other_user}","gists_url":"https://api.github.com/users/neoclust/gists{/gist_id}","starred_url":"https://api.github.com/users/neoclust/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/neoclust/subscriptions","organizations_url":"https://api.github.com/users/neoclust/orgs","repos_url":"https://api.github.com/users/neoclust/repos","events_url":"https://api.github.com/users/neoclust/events{/privacy}","received_events_url":"https://api.github.com/users/neoclust/received_events","type":"User","site_admin":false},"repo":{"id":59030449,"name":"pulse","full_name":"neoclust/pulse","owner":{"login":"neoclust","id":285923,"avatar_url":"https://avatars.githubusercontent.com/u/285923?v=3","gravatar_id":"","url":"https://api.github.com/users/neoclust","html_url":"https://github.com/neoclust","followers_url":"https://api.github.com/users/neoclust/followers","following_url":"https://api.github.com/users/neoclust/following{/other_user}","gists_url":"https://api.github.com/users/neoclust/gists{/gist_id}","starred_url":"https://api.github.com/users/neoclust/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/neoclust/subscriptions","organizations_url":"https://api.github.com/users/neoclust/orgs","repos_url":"https://api.github.com/users/neoclust/repos","events_url":"https://api.github.com/users/neoclust/events{/privacy}","received_events_url":"https://api.github.com/users/neoclust/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/neoclust/pulse","description":"Management Console","fork":true,"url":"https://api.github.com/repos/neoclust/pulse","forks_url":"https://api.github.com/repos/neoclust/pulse/forks","keys_url":"https://api.github.com/repos/neoclust/pulse/keys{/key_id}","collaborators_url":"https://api.github.com/repos/neoclust/pulse/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/neoclust/pulse/teams","hooks_url":"https://api.github.com/repos/neoclust/pulse/hooks","issue_events_url":"https://api.github.com/repos/neoclust/pulse/issues/events{/number}","events_url":"https://api.github.com/repos/neoclust/pulse/events","assignees_url":"https://api.github.com/repos/neoclust/pulse/assignees{/user}","branches_url":"https://api.github.com/repos/neoclust/pulse/branches{/branch}","tags_url":"https://api.github.com/repos/neoclust/pulse/tags","blobs_url":"https://api.github.com/repos/neoclust/pulse/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/neoclust/pulse/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/neoclust/pulse/git/refs{/sha}","trees_url":"https://api.github.com/repos/neoclust/pulse/git/trees{/sha}","statuses_url":"https://api.github.com/repos/neoclust/pulse/statuses/{sha}","languages_url":"https://api.github.com/repos/neoclust/pulse/languages","stargazers_url":"https://api.github.com/repos/neoclust/pulse/stargazers","contributors_url":"https://api.github.com/repos/neoclust/pulse/contributors","subscribers_url":"https://api.github.com/repos/neoclust/pulse/subscribers","subscription_url":"https://api.github.com/repos/neoclust/pulse/subscription","commits_url":"https://api.github.com/repos/neoclust/pulse/commits{/sha}","git_commits_url":"https://api.github.com/repos/neoclust/pulse/git/commits{/sha}","comments_url":"https://api.github.com/repos/neoclust/pulse/comments{/number}","issue_comment_url":"https://api.github.com/repos/neoclust/pulse/issues/comments{/number}","contents_url":"https://api.github.com/repos/neoclust/pulse/contents/{+path}","compare_url":"https://api.github.com/repos/neoclust/pulse/compare/{base}...{head}","merges_url":"https://api.github.com/repos/neoclust/pulse/merges","archive_url":"https://api.github.com/repos/neoclust/pulse/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/neoclust/pulse/downloads","issues_url":"https://api.github.com/repos/neoclust/pulse/issues{/number}","pulls_url":"https://api.github.com/repos/neoclust/pulse/pulls{/number}","milestones_url":"https://api.github.com/repos/neoclust/pulse/milestones{/number}","notifications_url":"https://api.github.com/repos/neoclust/pulse/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/neoclust/pulse/labels{/name}","releases_url":"https://api.github.com/repos/neoclust/pulse/releases{/id}","deployments_url":"https://api.github.com/repos/neoclust/pulse/deployments","created_at":"2016-05-17T14:36:08Z","updated_at":"2016-05-17T14:36:18Z","pushed_at":"2016-06-01T12:57:42Z","git_url":"git://github.com/neoclust/pulse.git","ssh_url":"git@github.com:neoclust/pulse.git","clone_url":"https://github.com/neoclust/pulse.git","svn_url":"https://github.com/neoclust/pulse","homepage":"","size":144771,"stargazers_count":0,"watchers_count":0,"language":"Python","has_issues":false,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":6,"forks":0,"open_issues":6,"watchers":0,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/neoclust/pulse/pulls/6"},"html":{"href":"https://github.com/neoclust/pulse/pull/6"},"issue":{"href":"https://api.github.com/repos/neoclust/pulse/issues/6"},"comments":{"href":"https://api.github.com/repos/neoclust/pulse/issues/6/comments"},"review_comments":{"href":"https://api.github.com/repos/neoclust/pulse/pulls/6/comments"},"review_comment":{"href":"https://api.github.com/repos/neoclust/pulse/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/neoclust/pulse/pulls/6/commits"},"statuses":{"href":"https://api.github.com/repos/neoclust/pulse/statuses/a129f05ea8374422091d8dff0c7c42455643dcd0"}}}}
{"actor":{"display_login":"neoclust"}}