'''
Created on Apr 09, 2011
Modified on May 31, 2012
@author: 'Dilum Bandara'
@version: '0.2'
@contact: dilumb@engr.colostate.edu'
@license: Apache License v2.0

   Copyright 2012 H. M. N. Dilum Bandara and Anura P. Jayasumana, Colorado State
   University

   Licensed under the Apache License, Version 2.0 (the "License");
   you may not use this file except in compliance with the License.
   You may obtain a copy of the License at

       http://www.apache.org/licenses/LICENSE-2.0

   Unless required by applicable law or agreed to in writing, software
   distributed under the License is distributed on an "AS IS" BASIS,
   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   See the License for the specific language governing permissions and
   limitations under the License.
'''

import BaseConfig

class ReadData(object):
    '''
    Read data class. Read resource attributes & queries from input files
    '''
    def __init__(self, resFile, queFile):
        '''
        Constructor        
        @param res_file: Resource file name
        @param que_file: Query file name
        '''
        self.fdInRes = open(resFile, 'r')
        self.fdInQue = open(queFile, 'r')        
        #Read 1st line containing attribute names
        self._attSet = self.fdInRes.readline().split()


    def __del__(self):
        '''
        Destructor
        '''
        self.fdInRes.close()
        self.fdInQue.close()


    def getResource(self):
        '''
        Read resource attribute set of a node
        @return: List of attributes. [[att name, value], ..., [att name, value]]
        [] if no data
        '''
        tmp = self.fdInRes.readline()
        if len(tmp) == 0: return []
        tmpAtts = tmp.split()
        atts = []
        for i in range(len(tmpAtts)): #Construct list of attributes
            if self._attSet[i] == 'nid': tmpAtts[i] = int(tmpAtts[i])
            elif self._attSet[i] == 'time': tmpAtts[i] = float(tmpAtts[i])
            elif self._attSet[i] == 'RspT': tmpAtts[i] = float(tmpAtts[i])
            elif self._attSet[i] == 'SIn': tmpAtts[i] = int(tmpAtts[i])
            elif self._attSet[i] == 'SOut': tmpAtts[i] = int(tmpAtts[i])
            elif self._attSet[i] == 'SUsed': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'DIn': tmpAtts[i] = int(tmpAtts[i])
            elif self._attSet[i] == 'DOut': tmpAtts[i] = int(tmpAtts[i])
            elif self._attSet[i] == 'DSvc': tmpAtts[i] = float(tmpAtts[i])
            elif self._attSet[i] == 'DUtil': tmpAtts[i] = float(tmpAtts[i])
            elif self._attSet[i] == 'DUsed': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'DFree': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'DSize': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'UpT': tmpAtts[i] = float(tmpAtts[i])
            elif self._attSet[i] == '1mLd': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == '5mLd': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == '15mLd': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'TMax': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'TAve': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'MFree': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'MSize': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'MAct': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'KVer': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'CFree': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'CSp': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'NCore': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'CorePC': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'FCName': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'Tx': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'Rx': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'Boot': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'NType': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'BWLim': 
                if tmpAtts[i] == 'none': tmpAtts[i] = BaseConfig.MAX_BW_LIMIT
                else: tmpAtts[i] = int(tmpAtts[i])
            elif self._attSet[i] == 'Lati': 
                if tmpAtts[i] == 'None': tmpAtts[i] = BaseConfig.MIN_LATITUDE
                else: tmpAtts[i] = float(tmpAtts[i])
            elif self._attSet[i] == 'Longi':
                if tmpAtts[i] == 'None': tmpAtts[i] = BaseConfig.MIN_LONGITUDE
                else: tmpAtts[i] = float(tmpAtts[i])
            elif self._attSet[i] == 'Loc': tmpAtts[i] = int(tmpAtts[i])                
            elif self._attSet[i] == 'Drift': tmpAtts[i] = float(tmpAtts[i])                
            elif self._attSet[i] == 'cusAtt': tmpAtts[i] = int(tmpAtts[i])
            else: 
                assert(False), 'Unmatched attribute in resources ' + \
                    self._attSet[i]
            atts.append([self._attSet[i], tmpAtts[i]])
        return atts 


    def getQuery(self):
        '''
        Read next query
        @return: Query as a list. [num of required resources, [att name 
         min val, max val], ..., [att name, min val, max val]], [] if no data
        '''
        tmpLine = self.fdInQue.readline().split()
        if len(tmpLine) == 0: return []
        query = [[tmpLine[0], int(tmpLine[1])]] #set no of required resources
        tmpAttrib = []
        for i in range(2, len(tmpLine)): #read attribute name, min, max
            if (i % 3) == 2: #Read starting from 3rd entry
                if tmpLine[i] == 'RspT' or tmpLine[i] == 'UpT':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'SIn' or tmpLine[i] == 'SOut':
                    tmpAttrib = [tmpLine[i], int(tmpLine[i + 1]), \
                                  int(tmpLine[i + 2])]
                elif tmpLine[i] == 'DIn' or tmpLine[i] == 'DOut':
                    tmpAttrib = [tmpLine[i], int(tmpLine[i + 1]), \
                                  int(tmpLine[i + 2])]
                elif tmpLine[i] == 'DSvc' or tmpLine[i] == 'DUtil':
                        tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                      float(tmpLine[i + 2])]
                elif tmpLine[i] == '1mLd' or tmpLine[i] == '5mLd' or \
                        tmpLine[i] == '15mLd':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'TMax' or tmpLine[i] == 'TAve':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'DUsed' or tmpLine[i] == 'DFree':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'DSize' or tmpLine[i] == 'MSize':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'MAct' or tmpLine[i] == 'MFree' \
                        or tmpLine[i] == 'SUsed':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'CFree' or tmpLine[i] == 'CSp':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'NCore' or tmpLine[i] == 'CorePC':
                    tmpAttrib = [tmpLine[i], int(tmpLine[i + 1]), \
                                  int(tmpLine[i + 2])]
                elif tmpLine[i] == 'Tx' or tmpLine[i] == 'Rx':
                    tmpAttrib = [tmpLine[i], int(tmpLine[i + 1]), \
                                  int(tmpLine[i + 2])]                    
                elif tmpLine[i] == 'Boot' or tmpLine[i] == 'NType' or \
                        tmpLine[i] == 'KVer' or tmpLine[i] == 'FCName':
                    tmpAttrib = [tmpLine[i], int(tmpLine[i + 1]), \
                                  int(tmpLine[i + 2])]
                elif tmpLine[i] == 'BWLim' or tmpLine[i] == 'Loc':
                    tmpAttrib = [tmpLine[i], int(tmpLine[i + 1]), \
                                  int(tmpLine[i + 2])]
                elif tmpLine[i] == 'Lati' or tmpLine[i] == 'Longi' \
                        or tmpLine[i] == 'Drift':
                    tmpAttrib = [tmpLine[i], float(tmpLine[i + 1]), \
                                  float(tmpLine[i + 2])]
                elif tmpLine[i] == 'cusAtt': #Custom attribute
                    tmpAttrib = [tmpLine[i], int(tmpLine[i + 1]), \
                                  int(tmpLine[i + 2])]                    
                else:
                    assert(False), 'Unmatched attribute in queries '+ tmpLine[i]
                query.append(tmpAttrib)
                tmpAttrib = []
        return query