#! /usr/bin/env python3
import sys
import os
import argparse
import subprocess
################################################################################
# Compile script for Manyo-lib release version
#    ver 20240212
#    written by Y. Inamura
#########################################################################
"""
Usage :     python3 do_make_Manyo.py <command> [options]
       command: [depend/man/make/install/clean]
       options: --debug --help --prefix --manyo-path
                --other-modules --numth --pyver
                --rev --without-depend --with-para --without-para
                --oldinstalltype
  -------------------------------------------------------
  depend  : depend script
  man     : script to make manual
  make    : make
  install : make install
  clean   : make clean

  --debug          : debug mode
  --help           : show this help
  --prefix=/hoge/hogege/hoge
                   : set directory to install
  --manyo-path=/hoge/hogege/hoge
                   : set directory to install with old structures
  --dist-name=Ubuntu
                   : Linux distribution name [RH6,RH7,Ubuntu]
  --other-modules=
                   : required other modules if need

  --numth=n        : set the number of multi-threading
  --pyver=n.m      : set python version
                     If not set pyver, the version of python executing this is used
  --rev=nnnn       : set revision number if need
  --without-depend : does not run depend script
  --with-para      : use compile option of -j
  --without-para   : not use compile option of -j (default)
  --oldinstalltype : install to old path (/opt/mlfsfot/)

"""

#########################################################################
#   CXX            : compiler
#   PYVER          : version of python
#   NUM_OF_THREADS : number of threading
#   PREFIX         : path to install
#   OTHER_MANYO_PAC: Other Manyo Package names required by compile
#   ENV_FILE_NAME  : file name of shell script to set Manyo environment
#   EXT_LIB_ROOT   : root path to external library required by Manyo-lib
#   DIST_NAME      : name of linux distribution
#########################################################################
CXX = "g++"
# PYVER          = "%s.%s"%(sys.version_info[0],sys.version_info[1])
PYVER = ""
try:
    PYVER = "{:d}.{:d}".format(sys.version_info.major, sys.version_info.minor)
except:
    pass

NUM_OF_THREADS = 8
PREFIX = "/opt/mlfsoft/utsusemi"
OTHER_MANYO_PAC = ["Utsusemi"]
ENV_FILE_NAME = "bashrc.manyo.release"
EXT_LIB_ROOT = "/usr/local"
DIST_NAME = ""
FOUND_DIST_NAME = ""
if os.path.exists("/etc/redhat-release"):
    f = open("/etc/redhat-release", "r")
    r=f.readline()
    f.close()
    p = r.split(" ")[-2]
    if p > "7":
        FOUND_DIST_NAME = "RH7"
    else:
        FOUND_DIST_NAME = "RH6"
elif os.path.exists("/etc/os-release"):
    fo = open("/etc/issue", "r")
    t = fo.readline()
    fo.close()
    v = t.split(' ')
    if v[1].find("24.04") == 0 or v[1].find("22.04") == 0 or v[1].find("20.04") == 0 or v[1].find("19.") == 0:
        FOUND_DIST_NAME = "Ubuntu20"
    elif v[1].find("18.04") == 0 or v[1].find("17.") == 0 or v[1].find("16.04") == 0 or v[1].find("15.") == 0:
        FOUND_DIST_NAME = "Ubuntu16"
    print("## Ubuntu version = {}".format(DIST_NAME))
else:
    pass

isDebug = False
isWithDepend = True
isCompPara = False
isNotManyoCore = True
isOldInstallType = False
if sys.version_info.major==2:
    isOldInstallType = True

manyo_rev = 0
if "MANYO_REV" in os.environ:
    manyo_rev = int(os.environ["MANYO_REV"])
else:
    try:
        cp = subprocess.run("git log -1 --date=short|grep 'Date:'", shell=True, capture_output=True, encoding="utf-8")
        if cp.stderr == '':
            latest_date_git = cp.stdout.split()[1]
            latest_date_v = latest_date_git.split("-")
            manyo_rev = int(latest_date_v[0][-2:] + latest_date_v[1] + latest_date_v[2])
    except:
        pass

#############################################
# Check arguments
#############################################

do_command = ""

parser = argparse.ArgumentParser(description="The script to compile manyo library source codes")

parser.add_argument('command', choices=['depend', 'man', 'make', 'install', 'clean'],
                    help='command in [depend/man/make/install/clean]')
parser.add_argument('--prefix', help='set MLFSOFT_PATH')
parser.add_argument('--manyo-path', help='set MANYO_PATH')
parser.add_argument('--dist-name',
                    choices=["RH6", "RH7", "RH", "Ubuntu", "Ubuntu16", "Ubuntu18", "Ubuntu20", "Ubuntu22", "Ubuntu24"],
                    help="Disribution name")
parser.add_argument('--other-modules', help="Other modules required if need.")
parser.add_argument('--numth', type=int, help='set the number of multi-threading', default=NUM_OF_THREADS)
tp = lambda x:list(map(int, x.split('.')))
parser.add_argument('--pyver', type=tp, help='Python version')
parser.add_argument('--rev', help='revision number default:YYYYMMDD')
parser.add_argument('--with-para', action='store_true', help='do make command with option -j')
parser.add_argument('--without-para', action='store_true', help='do make command without option -j')
parser.add_argument('--without-depend', action='store_false', help='Not do depend script')
parser.add_argument('--debug', action='store_true', help='turn on the debug mode')

args = parser.parse_args()

do_command = args.command
if args.manyo_path is not None:
    PREFIX = args.manyo_path
    isOldInstallType = True
elif args.prefix is not None:
    PREFIX = args.prefix
    isOldInstallType = False
else:
    print("Syntax error : option --prefix or --manyo-path is required.")
    sys.exit(-1)
isDebug = args.debug
isWithDepend = args.without_depend
if args.with_para and (not args.without_para):
    isCompPara = True
else:
    isCompPara = False
if args.rev is not None:
    manyo_rev = args.rev
if args.pyver is not None:
    PYVER = "{}.{}".format(args.pyver[0], args.pyver[1])
if args.numth is not None:
    NUM_OF_THREADS = args.numth
if args.other_modules is not None:
    other_mods = args.other_modules.split(",")
    OTHER_MANYO_PAC.extend(other_mods)
    for a_mod in OTHER_MANYO_PAC:
        print("OTHER_MANYO_PAC= {}".format(a_mod))

if args.dist_name is None:
    DIST_NAME = FOUND_DIST_NAME
else:
    DIST_NAME = args.dist_name
    if DIST_NAME == "" or DIST_NAME == "RH" or DIST_NAME == "Ubuntu":
        DIST_NAME = FOUND_DIST_NAME
    elif DIST_NAME == "Ubuntu18":
        DIST_NAME = "Ubuntu16"
    elif DIST_NAME == "Ubuntu22" or DIST_NAME == "Ubuntu24":
        DIST_NAME = "Ubuntu20"
if DIST_NAME == "":
    print("## ERROR : Not found distribution name")
    sys.exit(-1)

print("do_command = {}".format(do_command))
print("isDebug = ", isDebug)
print("isWithDepend = ", isWithDepend)
print("isCompPara = ", isCompPara)
print("manyo_rev = {}".format(manyo_rev))
print("PYVER = {}".format(PYVER))
if isOldInstallType:
    print("MANYO_PATH = {}".format(PREFIX))
else:
    print("PREFIX = {}".format(PREFIX))
print("OTHER_MANYO_PAC = ", OTHER_MANYO_PAC)
print("DIST_NAME = {}".format(DIST_NAME))

if (do_command == "clean"):
    isWithDepend = False

if (do_command == "make"):
    do_command = ""

if os.path.exists(os.path.join(os.getcwd(), "core")):
    isNotManyoCore = False

#############################################
# Check compile target ( manyo-core or not )
#############################################
if isNotManyoCore:
    PACKAGE_NAME = ""
    if os.path.exists(os.path.join(os.getcwd(), "Makefile")):
        fo = open(os.path.join(os.getcwd(), "Makefile"), "r")
        ll = fo.readlines()
        fo.close()
        for aline in ll:
            print(aline)
            if aline.find("PACKAGE_NAME") != -1:
                PACKAGE_NAME = aline.split("=")[1].strip()
                break
    if PACKAGE_NAME == "":
        print("Makefile is invalid. (No PACKAGE_NAME)")
        sys.exit(1)


#########################################################################
# execute make or make install
#############################################
OTHER_MAN_PAC = []
for pac in OTHER_MANYO_PAC:
    OTHER_MAN_PAC.append(pac)

EXT_LIB_PATH = os.path.join(EXT_LIB_ROOT, "lib")
EXT_INC_PATH = os.path.join(EXT_LIB_ROOT, "include")

if DIST_NAME.find("Ubuntu") == 0:
    DIST_PACK = "dist-packages"
else:
    DIST_PACK = "site-packages"

com = ""
if isOldInstallType:
    MANYO_PATH = PREFIX
    com += "export MANYO_PATH={};".format(MANYO_PATH)
    com += "export LIBRARY_PATH=${{MANYO_PATH}}/lib:{};".format(EXT_LIB_PATH)
    com += "export LD_LIBRARY_PATH=${LIBRARY_PATH};"
    com += "export C_INCLUDE_PATH=/usr/include/python{}:".format(PYVER)
    com += ":${MANYO_PATH}/include" + ":{}".format(EXT_INC_PATH)
    for m_pac_name in OTHER_MAN_PAC:
        com += ":${MANYO_PATH}/include/" + "{}".format(m_pac_name)
else:
    MANYO_PATH = os.path.join(PREFIX, "lib", "python{}".format(PYVER), DIST_PACK)
    com += "export MANYO_PATH={};".format(MANYO_PATH)
    com += "export PREFIX={};".format(PREFIX)
    com += "export LIBRARY_PATH=${MANYO_PATH}:" + "{};".format(EXT_LIB_PATH)
    com += "export LD_LIBRARY_PATH=${LIBRARY_PATH};"
    com += "export C_INCLUDE_PATH=/usr/include/python{}:".format(PYVER)
    com += ":${PREFIX}/include/Manyo" + ":{}".format(EXT_INC_PATH)
    for m_pac_name in OTHER_MAN_PAC:
        com += ":${PREFIX}/include/Manyo/" + "{}".format(m_pac_name)

if DIST_NAME.find("Ubuntu20") == 0:
    com += ":/usr/include/hdf5/serial;" ## [inamura 201103 for Ubuntu 20.04]
elif DIST_NAME.find("Ubuntu16") == 0: # for Ubuntu 16 or 18
    com += ":/usr/include/hdf5/serial;" ## [inamura 201103 for Ubuntu 16.04 and 18.04]
else: ## For RH
    com += "; "

com += 'export INC_EXT="'
for m_pac_name in OTHER_MAN_PAC:
    com += "%s "%(m_pac_name)
com += '"; '
com += "export CPLUS_INCLUDE_PATH=${C_INCLUDE_PATH};"

if isWithDepend:
    if isNotManyoCore:
        com += "./depend; "
    else:
        com += 'cd core; ./depend; cd ../MLF; ./depend; cd ../SerialPySrv; ./depend; cd ..; '

if (do_command != "depend"):
    com += 'make {:s} '.format(do_command)
    if isCompPara:
        com += ' -j '
    if DIST_NAME == "":
        DIST_NAME = "Ubuntu"
    com += ' DIST_NAME={:s}'.format(DIST_NAME)
    if PYVER != "":
        com += ' CXX={:s} PyVer={:s} NUM_MULTH={:d}'.format(CXX, PYVER, NUM_OF_THREADS)
    else:
        com += ' CXX={:s} NUM_MULTH={:d}'.format(CXX, NUM_OF_THREADS)
    com += ' MANYO_REV={:d}'.format(manyo_rev)
    if not isOldInstallType and PYVER != "":
        com += " PY_PREFIX={}".format(MANYO_PATH)

print("command = {}".format(com))
if isDebug:
    pass
else:
    retcode = os.system(com)
    if retcode:
        sys.stderr.write("Return code '{}', is not 0.\n".format(retcode))
        raise RuntimeError("Error has been caused in building.")


#########################################################################
# make environ file
#############################################

env_list = []
env_list.append('#!/bin/bash')
env_list.append('export MANYO_PATH={:s}'.format(MANYO_PATH))

if isOldInstallType:
    env_list.append('export LD_LIBRARY_PATH=${MANYO_PATH}/lib:${LD_LIBRARY_PATH}')
else:
    env_list.append('export LD_LIBRARY_PATH=${MANYO_PATH}:${LD_LIBRARY_PATH}')

if isNotManyoCore:
    env_list.append('export PYTHONPATH=${MANYO_PATH}:${MANYO_PATH}/Manyo/' + '%s:'.format(PACKAGE_NAME) + '${PYTHONPATH}')
else:
    env_list.append( 'export PYTHONPATH=${MANYO_PATH}:${PYTHONPATH}' )
env_list.append( 'export PATH={}/bin:$PATH'.format(PREFIX) )


if isDebug:
    for an_env in env_list:
        print(an_env)
else:
    fo = open(os.path.join(os.getcwd(), ENV_FILE_NAME), 'w')
    for ss in env_list:
        fo.write(ss + '\n')
    fo.close()
