#!/usr/bin/python

import sys
import json
import os
import shutil
import glob
import re
from collections import OrderedDict

def check_file_exist (file):
    if not os.path.exists(file):
        printstr = "Error: " + file + " does not exist, please check!\n"
        print(printstr)
        exit (1)

debug        = sys.argv[1] # True/False
project      = sys.argv[2] # project name
flavor       = sys.argv[3] # flavor name
dsp_project  = sys.argv[4] # dsp project name
dsp_flavor   = sys.argv[5] # dsp flavor name
modis_uesim  = sys.argv[6] # check modis or uesim
inputTarget    = sys.argv[7] # currect Target Name
outputTarget   = sys.argv[8] # output Target Name
chk_append_opt = sys.argv[9].split(',') # special option
targetName     = os.path.basename(inputTarget)


input_json = "tools/genTargetFile/all_dep.json"
build_fdr  = "build/" + project + "/" + flavor
if modis_uesim == 'target':
    outputFdr  = build_fdr + "/bin/json"
else:
    outputFdr = build_fdr + "/" + modis_uesim + "/_BUILD_XGEN/bin/json"

encode_enable = True
if sys.version_info[0] >= 3:
  encode_enable = False

if debug:
    print ("\n**********************************************************")
    print("Project Name  = %s" % project)
    print("Flavor Name   = %s" % flavor)
    print("DSP Project Name  = %s" % dsp_project)
    print("DSP Flavor Name   = %s" % dsp_flavor)
    print("Input Target  = %s" % inputTarget)
    print("Output Target = %s" % outputTarget)
    print("Target NAme   = %s" % targetName)
    print ("")

input_target_jason = "tools/genTargetFile/json/" + targetName + ".json"
TargetFileList   = []
PrerequisiteList = []

if targetName != "genJson.det":
    check_file_exist(input_target_jason)
    str = outputTarget + ': ' + input_target_jason
    TargetFileList = [str]
    PrerequisiteList = [input_target_jason]
if debug:
    InputFileList  = [input_target_jason]
    OutputFileList = []
with open(input_target_jason , 'r') as reader:
    JsonData = json.loads(reader.read(), object_pairs_hook=OrderedDict)

    for option in chk_append_opt:
        for Script_List in JsonData[option]:
            if Script_List != "NONE":
                check_file_exist(Script_List)
                str = outputTarget + ': ' + Script_List
                TargetFileList.append(str)
                PrerequisiteList.append(Script_List)
            JsonInputList = JsonData[option][Script_List]['InputFile']['common']
            if modis_uesim == 'target':
                JsonInputList += JsonData[option][Script_List]['InputFile']['target']
            else:
                JsonInputList += JsonData[option][Script_List]['InputFile']['modis_uesim']
            for File_List in JsonInputList:
                File_List = File_List.replace('$proj',project).replace('$flavor',flavor).replace('$dsp_proj',dsp_project).replace('$dsp_flavor',dsp_flavor).replace('$modis_uesim',modis_uesim)
                Glob_File_List = glob.glob(File_List)
                if Glob_File_List:
                    for file in Glob_File_List:
                        FinalInput = file
                        str = outputTarget + ': ' + FinalInput
                        TargetFileList.append(str)
                        PrerequisiteList.append(FinalInput)
                        if debug:
                            InputFileList.append(FinalInput)
                else:
                    check_file_exist(File_List)

            if debug:
                if modis_uesim == 'target':
                    JsonOutputList = JsonData[option][Script_List]['OutputFile']['target']
                else:
                    JsonOutputList = JsonData[option][Script_List]['OutputFile']['modis_uesim']
                for File_List in JsonOutputList:
                    File_List = File_List.replace('$proj',project).replace('$flavor',flavor).replace('$dsp_proj',dsp_project).replace('$dsp_flavor',dsp_flavor).replace('$modis_uesim',modis_uesim)
                    for file in glob.glob(File_List):
                        FinalOutput = file
                        OutputFileList.append(FinalOutput)

with open(outputTarget , 'a+') as writer:
    writer.write('\n')
    for item in TargetFileList:
        if debug:
            print(item)
        writer.write(item + '\n')
    writer.write('\n')
    for item in PrerequisiteList:
        if debug:
            print(item)
        writer.write(item + ':\n')

if debug:
    print("\nInputFile:")
    for item in InputFileList:
        print(item)

    print("\nOutputFile:")
    for item in OutputFileList:
        print(item)
    print ("**********************************************************\n")
