Commit 9a2f2a4d authored by canterburym's avatar canterburym
Browse files

Updating ASN.1 testing to include R19

parent 919c2e9d
Loading
Loading
Loading
Loading
Loading
+6 −1
Original line number Diff line number Diff line
@@ -9,5 +9,10 @@
        "./testing/dependencies/asn/IPAccessPDU.asn",
        "./testing/dependencies/asn/stubs/LI-PS-PDU.asn"
    ],
    ["./33128/r18/TS33128IdentityAssociation.asn"]
    ["./33128/r18/TS33128IdentityAssociation.asn"],
    [
        "./33128/r19/TS33128Payloads.asn",
        "./testing/dependencies/asn/IPAccessPDU.asn",
        "./testing/dependencies/asn/stubs/LI-PS-PDU.asn"
    ]
]
+86 −77
Original line number Diff line number Diff line
#!/usr/bin/env python3

import logging
import os
import json
from pathlib import Path
from subprocess import run
@@ -9,17 +6,17 @@ from shutil import which

from pycrate_asn1c.asnproc import *

import lint_asn1

def reconstrainInteger (filename):
    Path('temp.asn').write_text(Path(filename).read_text().replace("18446744073709551615", "65536"))
    return 'temp.asn'

filesWithBigInts = [
    'testing/dependencies/asn/stubs/LI-PS-PDU.asn',
    'testing/dependencies/asn/IPAccessPDU.asn'
    '102232-1/LI-PS-PDU.asn',
    '102232-3/IPAccessPDU.asn',
    '102232-4/L2AccessPDU.asn'
]

asn1c_path = ""
change_path_to_unix = False

def fix_path(path):
@@ -43,10 +40,10 @@ def syntaxCheckASN(fileList):
        try:
            if file.as_posix() in filesWithBigInts:
                newFile = reconstrainInteger(str(file))
                p = run(["asn1c", '-E', fix_path(newFile)], capture_output=True)
                p = run([asn1c_path, '-E', fix_path(newFile)], capture_output=True)
                Path(newFile).unlink()
            else:
                p = run(["asn1c", '-E', fix_path(str(file))], capture_output=True)
                p = run([asn1c_path, '-E', fix_path(str(file))], capture_output=True)
            if (p.returncode != 0):
                errorMessage = p.stderr.decode().splitlines()[0]
                if errorMessage.startswith('   Value "18446744073709551615" at line'):
@@ -70,6 +67,28 @@ def syntaxCheckASN(fileList):
            }
    return results


duplicateObjects = {
    '102232-1/LI-PS-PDU.asn' : [
        'CCPayload',
        'IRIPayload',
        'Location'
    ],
    'testing/mod1.asn' : [
        'ClashField'
    ]
}
def fixDuplicateObjects(filename):
    stringContent = filename.read_text()
    for object in duplicateObjects[filename.as_posix()]:
        stringContent = stringContent.replace(f'{object} ::=', f'Native{object} ::=')
        stringContent = stringContent.replace(f'SEQUENCE OF {object}', f'SEQUENCE OF Native{object}')
        #stringContent = sub(f"]\\w{object}", f"] Native{object}", stringContent)

    Path('temp.asn').write_text(stringContent)
    return 'temp.asn'


def compileAllTargets (compileTargets):
    """
    Attempts to compile a set of compile targets using the pycrate ASN1 tools
@@ -97,24 +116,30 @@ def compileAllTargets(compileTargets):
            fileNames = []
            GLOBAL.clear()
            for filename in target:
                with open(filename) as f:
                    fileTexts.append(f.read())
                    fileNames.append(str(filename))
                pFile = Path(filename)
                if pFile.as_posix() in duplicateObjects:
                    tmpFile = Path(fixDuplicateObjects(pFile))
                    fileTexts.append(tmpFile.read_text())
                    #tmpFile.unlink()
                else:
                    fileTexts.append(pFile.read_text())
                fileNames.append(filename)
                logging.debug (f"  Loading {filename}")
            compile_text(fileTexts, filenames = fileNames)
            results[str(firstTarget)] = {
                "ok": True,
                'ok' : True,
            }
        except Exception as ex:
            results[str(firstTarget)] = {
                "ok": False,
                "code": -1,
                "message": f"{ex!r}",
                'ok'   : False,
                'code' : -1,
                'message'  : f"{ex!r}"
            }
            continue
    return results



def processResults (results, stageName):
    """
    Counts the number of errors and writes out the output per filename
@@ -124,7 +149,7 @@ def processResults(results, stageName):
    :returns: The number of files which had errors
    """    
    print("")
    errorCount = sum([1 for r in results.values() if not r["ok"]])
    errorCount = sum([1 for r in results.values() if not r['ok']])
    logging.info(f"{errorCount} {stageName} errors encountered")
    
    print(f"{'-':-<60}")
@@ -132,9 +157,9 @@ def processResults(results, stageName):
    print(f"{'-':-<60}")
    for filename, result in results.items():
        print(f" {filename:.<55}{'..OK' if result['ok'] else 'FAIL'}")
        if not result["ok"]:
            if isinstance(result["message"], list):
                for thing in result["message"]:
        if not result['ok']:
            if isinstance(result['message'], list):
                for thing in result['message']:
                    print(f"    {thing['message']}")
            else:
                print(f"    {result['message']}")
@@ -146,33 +171,40 @@ def processResults(results, stageName):
    return errorCount


def main():
    loglevel = os.environ.get("LOGLEVEL", "WARNING").upper()
    logging.basicConfig(level=loglevel)
if __name__ == '__main__':
    logging.info ('Searching for ASN1C')
    asn1c_path = which("asn1c")
    if asn1c_path is None:
        raise Exception ("No asn1c executable found. Please install asn1c")
    logging.info (f"asn1c found at {asn1c_path}")
    if asn1c_path.lower().endswith("bat"):
        logging.info (f"asn1c is a batch file, so assume path separators need to be changed")
        change_path_to_unix = True
    

    logging.info("Searching for ASN.1 files")
    logging.info('Searching for ASN.1 files')
    fileList = list(Path(".").rglob("*.asn1")) + list(Path(".").rglob("*.asn"))
    logging.info(f"{len(fileList)} ASN.1 files found")
    logging.info(f'{len(fileList)} ASN.1 files found')
    for file in fileList:
        logging.debug(f"  {file}")
        logging.debug(f'  {file}')
    
    ignoreList = Path("testing/asn_ignore.txt").read_text().splitlines()
    ignoreList = Path('testing/asn_ignore.txt').read_text().splitlines()
    ignoredFiles = []
    for ignore in ignoreList:
        logging.debug(f"Ignoring pattern {ignore}")
        logging.debug(f'Ignoring pattern {ignore}')
        for file in fileList:
            if ignore in str(file):
                ignoredFiles.append(file)
                logging.debug(f" Ignoring {str(file)} as contains {ignore}")
    ignoredFiles = list(set(ignoredFiles))
    logging.info(f"{len(ignoredFiles)} files ignored")
    logging.info(f'{len(ignoredFiles)} files ignored')
    for file in ignoredFiles:
        logging.debug(f"  {file}")
        logging.debug(f'  {file}')
    
    fileList = [file for file in fileList if file not in ignoredFiles]
    logging.info(f"{len(fileList)} files to process")
    logging.info(f'{len(fileList)} files to process')
    for file in fileList:
        logging.debug(f"  {file}")
        logging.debug(f'  {file}')

    if len(fileList) == 0:
        logging.warning ("No files specified")
@@ -181,37 +213,14 @@ def main():
    logging.info("Parsing ASN1 files")
    parseResults = syntaxCheckASN(fileList)
    if processResults(parseResults, "Parsing") > 0:
        exit(1)
        exit(-1)

    logging.info ("Getting compile targets")
    compileTargets = json.loads(Path("testing/asn_compile_targets.json").read_text())
    compileTargets = json.loads(Path('testing/asn_compile_targets.json').read_text())
    logging.info (f"{len(compileTargets)} compile targets found")

    compileResults = compileAllTargets(compileTargets)
    if processResults(compileResults, "Compiling") > 0:
        exit(1)

    logging.info("Linting files")
    ignoreLintingList = Path("testing/asn_ignore_lint.txt").read_text().splitlines()
    ignoredFiles = []
    for ignore in ignoreLintingList:
        logging.debug(f"Ignoring pattern {ignore} for linting")
        for file in fileList:
            if ignore in str(file):
                ignoredFiles.append(file)
                logging.debug(f" Ignoring {str(file)} for linting as contains {ignore}")
    ignoredFiles = list(set(ignoredFiles))
    logging.info(f"{len(ignoredFiles)} files ignored for linting")
    for file in ignoredFiles:
        logging.debug(f"  {file}")
    fileList = [file for file in fileList if file not in ignoredFiles]
    lintExceptions = json.loads(Path("testing/asn_lint_exceptions.json").read_text())
    lintResults = lint_asn1.lintASN1Files(fileList, lintExceptions)
    if processResults(lintResults, "Linting") > 0:
        exit(1)
        exit(-1)
    
    exit(0)


if __name__ == "__main__":
    main()