
Imports System.IO
Imports System.Runtime.InteropServices

' *****
Imports EgtUILib
' *****

Module M_Fanuc

#Region " Classes"
#End Region

#Region " Enum"

   Public Enum CNC_Connection_Status_Type
      NOT_CONNECTED = 1
      CONNECTED = 2
   End Enum

   Public Enum CNC_Connection_Type
      HSSB = 1
      Ethernet = 2
   End Enum

   'PMC Area Type Mapping
   Public Enum PMCAreaType As Short

      G_AREA = 0
      F_AREA = 1
      Y_AREA = 2
      X_AREA = 3
      A_AREA = 4
      R_AREA = 5
      T_AREA = 6
      K_AREA = 7
      C_AREA = 8
      D_AREA = 9

   End Enum
#End Region

#Region " Constants"

   Const N_BYTE_TYPE As Short = 0
   Const N_INT_TYPE As Short = 1
   Const N_LONG_TYPE As Short = 2

   Const CUSTOM_MACRO_SIZE = 10
   Const BLOCK_SIZE = 256
   Const ONE_DATA_ONLY As Integer = 1

   Const ERR_READ_MACRO_EXPON As Integer = -9000

   Const MAX_CNC_ALM_MSG As Short = 10 ' max number of alarms
   Const MAX_OPERATOR_ALM_MSG As Short = 5 ' max number of messages
   Const ALL_ALARM_TYPE As Short = -1
   Const ALL_OP_MSG_TYPE As Short = -1
   Const ALL_AXES As Short = -1

   Public Const BAD_RETURN As Long = -99999
   Public Const BAD_RETURN_SH As Short = -999


#End Region

#Region " Structures"

   Public Structure CNC_Info_Type

      Dim name As String
      Dim IPAddress As String
      Dim Port As Short
      Dim Timeout As Integer
      Dim Handle As UShort
      Dim ConnectionStatus As CNC_Connection_Status_Type
      Dim ConnectionType As CNC_Connection_Type
      Dim Node_number As Long

   End Structure


#End Region

#Region " Variabili "

   Private b_OM_pos As Boolean = True



   Public cnc_info As CNC_Info_Type
   Public bSimulation As Boolean
   Public b_machine_in_inches As Boolean

   Private h_last_cnc_info_handle As UShort
   Private h_Session As UShort            ' Handle


   Public AlarmMessage(MAX_CNC_ALM_MSG) As String
   Public AlarmNumber(MAX_CNC_ALM_MSG) As Integer
   Public AlarmMessageCount As Short

   Public OperatorMessage(MAX_CNC_ALM_MSG) As String
   Public OperatorMsgNumber(MAX_CNC_ALM_MSG) As Short
   Public OperatorMessageCount As Short

   Public sz_Err_Msg As String
   Public n_ret_code As Short

   Public sz_NC_type As String

   Public lst_plc_messages As New List(Of String)


   Public l_pos_values(Focas1.MAX_AXIS) As Long
   Public l_delta_values(Focas1.MAX_AXIS) As Long

   Private values() As Double = Nothing


   Private b_debugf As Boolean = False

#End Region

#Region " Connect"

   Function NC_connect(ByRef machine_cnc_info As CNC_Info_Type) As Int16
      With cnc_info

         sz_Err_Msg = ""

         If bSimulation Then
            Return Focas1.EW_OK
            .ConnectionStatus = CNC_Connection_Status_Type.CONNECTED

            sz_Err_Msg = " !! simulazione CN... "
            EgtOutLog(sz_Err_Msg)

         Else
            n_ret_code = Focas1.EW_SYSTEM2 ' tanto per dirne una

            If b_debugf Then
               sz_Err_Msg = " .IPAddress " & .IPAddress & " - " & " .Port " & .Port & " - " & " .Handle " & .Handle & " - " & " .Timeout " & .Timeout
               EgtOutLog(sz_Err_Msg)
            End If ' debug

            If .ConnectionType = CNC_Connection_Type.HSSB Then
               Try
                  n_ret_code = Focas1.cnc_allclibhndl2(.Node_number, .Handle)
               Catch e As Exception
                  sz_Err_Msg = "Error in M_fanuc - NCConnect HSSB" & " .Handle " & .Handle & "- ret code = " & n_ret_code.ToString & Environment.NewLine & e.Message
                  EgtOutLog(sz_Err_Msg)
               End Try
            Else
               Try
                  n_ret_code = -99
                  n_ret_code = Focas1.cnc_allclibhndl3(.IPAddress, .Port, .Timeout, .Handle)
               Catch e As Exception
                  sz_Err_Msg = "Error in M_fanuc - NCConnect Eth " & .IPAddress & " - " & " .Port " & .Port & " - " & " .Handle " & .Handle & "- ret code = " & n_ret_code.ToString & Environment.NewLine & e.Message
                  EgtOutLog(sz_Err_Msg)
               End Try
            End If


            '          EgtOutLog(" *** Focas1.cnc_allclibhndl3: " & n_ret_code)
            h_last_cnc_info_handle = .Handle
            h_Session = .Handle
#If False Then
                Dim vafbus As Focas1.ODBST
                n_ret_code = Focas1.cnc_statinfo(h_Session, vafbus)

                Dim odbaxis As Focas1.ODBAXIS = Nothing ' defaults to 8 in fwlib32.vb
                Dim n_size As Short

                sz_Err_Msg = ""
                n_size = 4 + 32 * 4 ' 4 + 4 * 8 

                ' n_ret_code = Focas1.cnc_relative2(h_Session, 1, n_size, odbaxis)
                'n_ret_code = Focas1.cnc_absolute2(h_Session, 1, n_size, odbaxis)
                n_ret_code = Focas1.cnc_machine(h_Session, ALL_AXES, n_size, odbaxis)

                If n_ret_code = Focas1.EW_OK Then
                    For n As Short = 0 To Focas1.MAX_AXIS - 1
                        l_pos_values(n) = odbaxis.data(n)
                    Next
                End If
#End If
            If (n_ret_code = Focas1.EW_OK) Then

               lst_plc_messages.Clear()

               Dim sz_temp As String = ""

               n_ret_code = F_Get_current_NC_dir(sz_temp)
               If n_ret_code <> Focas1.EW_OK Then Return n_ret_code

               .ConnectionStatus = CNC_Connection_Status_Type.CONNECTED
               Return Focas1.EW_OK
            Else
               sz_Err_Msg = "Error in NC_connect " & Fanuc_error_codes(n_ret_code)
               Return n_ret_code
            End If

         End If

      End With
   End Function

   Function NC_disconnect() As Int16
      With cnc_info

         If bSimulation Then
            .ConnectionStatus = CNC_Connection_Status_Type.NOT_CONNECTED
            Return Focas1.EW_OK
         Else
            h_last_cnc_info_handle = .Handle

            n_ret_code = Focas1.cnc_freelibhndl(.Handle)

            If (n_ret_code = Focas1.EW_OK) Then
               .ConnectionStatus = CNC_Connection_Status_Type.NOT_CONNECTED
               Return Focas1.EW_OK
            Else
               sz_Err_Msg = "Error in NC_disconnect " & Fanuc_error_codes(n_ret_code)
               Return n_ret_code
            End If

         End If

      End With
   End Function

#End Region

#Region " Error codes"

   Function Fanuc_error_codes(ByVal ncod As Integer) As String

      Dim odber As Focas1.ODBERR '
      Dim n As Integer, sz_Fanuc_error_cods As String

      sz_Fanuc_error_cods = "??????"

      Select Case ncod

         Case Focas1.EW_PROTOCOL
            sz_Fanuc_error_cods = "EW_PROTOCOL : protocol error (-17)"

         Case Focas1.EW_SOCKET
            sz_Fanuc_error_cods = "EW_SOCKET : Windows socket error (-16)"

         Case Focas1.EW_NODLL
            sz_Fanuc_error_cods = "EW_NODLL : DLL not exist error (-15)"

         Case Focas1.EW_BUS
            sz_Fanuc_error_cods = "EW_BUS : bus error (-11)"

         Case Focas1.EW_SYSTEM2
            sz_Fanuc_error_cods = "EW_SYSTEM2 : system error (-10)"

         Case Focas1.EW_HSSB
            sz_Fanuc_error_cods = "EW_HSSB : hssb communication error (-9)"

         Case Focas1.EW_HANDLE
            sz_Fanuc_error_cods = "EW_HANDLE : Windows library handle error (-8)"

         Case Focas1.EW_VERSION
            sz_Fanuc_error_cods = "EW_VERSION : EW_VERSION : CNC/PMC version mismatch (-7)"

         Case Focas1.EW_UNEXP
            sz_Fanuc_error_cods = "EW_UNEXP : abnormal error (-6)"

         Case Focas1.EW_SYSTEM
            sz_Fanuc_error_cods = "EW_SYSTEM : system error (-5)"

         Case Focas1.EW_PARITY
            sz_Fanuc_error_cods = "EW_PARITY : shared RAM parity error (-4)"

         Case Focas1.EW_MMCSYS
            sz_Fanuc_error_cods = "EW_MMCSYS : emm386 or mmcsys DRIVERS install error (-3)"

         Case Focas1.EW_RESET
            sz_Fanuc_error_cods = "EW_RESET : reset or stop occured error (-2)"

         Case Focas1.EW_BUSY
            sz_Fanuc_error_cods = "EW_BUSY : busy error (-1)"

         Case Focas1.EW_OK
            sz_Fanuc_error_cods = "no problem"

         Case Focas1.EW_FUNC
            sz_Fanuc_error_cods = "EW_FUNC : command prepare error OR pmc not exist (1)"

         Case Focas1.EW_LENGTH
            sz_Fanuc_error_cods = "EW_LENGTH : data block length error (2)"

         Case Focas1.EW_NUMBER
            sz_Fanuc_error_cods = "EW_NUMBER : data number error OR address range error (3)"

         Case Focas1.EW_ATTRIB
            sz_Fanuc_error_cods = " : data attribute error OR data type error (4)"


         Case Focas1.EW_DATA

            odber.err_dtno = ncod

            ' get detail error


            n = Focas1.cnc_getdtailerr(h_last_cnc_info_handle, odber)

            Select Case odber.err_no
               Case 1
                  sz_Fanuc_error_cods = "EW_DATA 5-1: Illegal character in NC program"
               Case 2
                  sz_Fanuc_error_cods = "EW_DATA 5-2: TV check, block with odd number of char"
               Case 3
                  sz_Fanuc_error_cods = "EW_DATA 5-3: registered program count is full"
               Case 4
                  sz_Fanuc_error_cods = "EW_DATA 5-4: program number already registered"
               Case 5
                  sz_Fanuc_error_cods = "EW_DATA 5-5: same program selected on CNC"
               Case Else
                  sz_Fanuc_error_cods = "EW_DATA : data error (5) - errno " & Str(odber.err_no)

            End Select

         Case Focas1.EW_NOOPT
            sz_Fanuc_error_cods = "EW_NOOPT : no option error (6)"

         Case Focas1.EW_PROT
            sz_Fanuc_error_cods = "EW_PROT : write protect error (7)"

         Case Focas1.EW_OVRFLOW
            sz_Fanuc_error_cods = "EW_OVRFLOW : memory overflow error (8)"

         Case Focas1.EW_PARAM
            sz_Fanuc_error_cods = "EW_PARAM : cnc parameter not correct error (9)"

         Case Focas1.EW_BUFFER
            sz_Fanuc_error_cods = "EW_BUFFER : buffer error (10)"

         Case Focas1.EW_PATH
            sz_Fanuc_error_cods = "EW_PATH : path error (11)"

         Case Focas1.EW_MODE
            sz_Fanuc_error_cods = "EW_MODE : cnc mode error (12)"

         Case Focas1.EW_REJECT
            sz_Fanuc_error_cods = "EW_REJECT : execution rejected error (13)"

         Case Focas1.EW_DTSRVR
            sz_Fanuc_error_cods = "EW_DTSRVR : data server error (14)"

         Case Focas1.EW_ALARM
            sz_Fanuc_error_cods = "EW_ALARM : alarm has occurred (15)"

         Case Focas1.EW_STOP
            sz_Fanuc_error_cods = "EW_STOP : CNC is not running (16)"

         Case Focas1.EW_PASSWD
            sz_Fanuc_error_cods = "EW_PASSWD : protection data error (17)"


                ' my codes
         Case ERR_READ_MACRO_EXPON
            sz_Fanuc_error_cods = "ERR_READ_MACRO_EXPON : excess exponent in readmacro (-9000)"

      End Select

      Return sz_Fanuc_error_cods

   End Function
   '
   ' riorna true se  file not found error... 
   '
   Function fanuc_error_file_not_found(ByVal ncod As Integer) As Boolean

      Dim odber As Focas1.ODBERR '
      Dim n As Integer

      If ncod = Focas1.EW_DATA Then

         odber.err_dtno = ncod

         n = Focas1.cnc_getdtailerr(h_last_cnc_info_handle, odber) ' get detail error

         If odber.err_no = 2 Then  '   Case 2 "EW_DATA 5-2: Specified folder cannot be found"
            Return True
         End If

      End If

      Return False

   End Function

#End Region

#Region " Read/write vars"
   ' ---------------------------------------------------------
   ' Legge una serie di Bytes dall' area PLC
   ' ---------------------------------------------------------
   Public Function F_Read_n_Bytes_From_PLC(ByVal nVar As Integer, ByVal PMC_area As PMCAreaType,
                                     ByRef Buffer As Byte(), ByVal n_bytes As Integer) As Boolean
      Dim iodb As Focas1.IODBPMC0 = Nothing
      Dim nLength As Short
      Dim n_s As UShort
      Dim n_e As UShort


      sz_Err_Msg = ""
      If Not bSimulation Then ' simulazione ?

         iodb.type_a = PMC_area
         iodb.type_d = N_BYTE_TYPE
         iodb.datano_s = nVar
         iodb.datano_e = nVar + n_bytes - 1

         n_s = nVar
         n_e = nVar + n_bytes - 1

         nLength = 8 + 1 * n_bytes

         n_ret_code = Focas1.pmc_rdpmcrng(h_Session, PMC_area, N_BYTE_TYPE, n_s, n_e, nLength, iodb)
         If (n_ret_code <> Focas1.EW_OK) Then
            sz_Err_Msg = "Error on reading n_bytes from variable D " & Str(nVar) & " - " & Fanuc_error_codes(n_ret_code)
            'szErrMsg = msg(119) & " " & Str(nVar) & " " & msg(120) & " " & Str(nError)
            'MsgBox(szErrMsg)
            Return False
         End If

         For n As Short = 0 To n_bytes - 1
            Buffer(n) = iodb.cdata(n)
         Next n

      Else

      End If ' simulazione

      Return True

   End Function

   ' ---------------------------------------------------------
   ' Legge una serie di short dall' area PLC
   ' ---------------------------------------------------------
   Public Function F_Read_n_Int_From_PLC(ByVal nVar As Integer, ByVal PMC_area As Short,
                                     ByRef Buffer As Short(), ByVal n_ints As Integer) As Boolean
      Dim iodb As Focas1.IODBPMC1 = Nothing
      Dim nLength As Short
      Dim n_s As UShort
      Dim n_e As UShort

      '       ReDim iodb.idata(10)

      sz_Err_Msg = ""
      If Not bSimulation Then ' simulazione ?

         iodb.type_a = PMC_area
         iodb.type_d = N_INT_TYPE
         iodb.datano_s = nVar

         n_s = nVar
         n_e = nVar + (2 * n_ints) - 1

         iodb.datano_e = n_e
         nLength = 8 + (2 * n_ints)

         n_ret_code = Focas1.pmc_rdpmcrng(h_Session, PMC_area, N_INT_TYPE, n_s, n_e, nLength, iodb)
         If (n_ret_code <> Focas1.EW_OK) Then
            sz_Err_Msg = "Error on reading n_int from variable D " & " - " & Fanuc_error_codes(n_ret_code)
            'szErrMsg = msg(119) & " " & Str(nVar) & " " & msg(120) & " " & Str(nError)
            'MsgBox(szErrMsg)
            Return False
         End If

         For n As Short = 0 To n_ints - 1
            Buffer(n) = iodb.idata(n)
         Next n
      Else

      End If ' simulazione

      Return True

   End Function

   ' ---------------------------------------------------------
   ' Scrive una serie di Bytes nell' area PLC 
   ' ---------------------------------------------------------
   Public Function F_Write_n_Bytes_To_PLC(ByVal nVar As Integer, ByVal PMC_area As PMCAreaType,
                                     ByRef Buffer As Byte(), ByVal n_bytes As Integer) As Boolean
      Dim n As Integer, nLength As Integer
      Dim iodb As Focas1.IODBPMC0 ' per scritture di bytes
      '
      sz_Err_Msg = ""
      If Not bSimulation Then ' simulazione ?

         iodb.type_a = PMC_area
         iodb.type_d = N_BYTE_TYPE
         iodb.datano_s = nVar
         iodb.datano_e = nVar + n_bytes - 1

         nLength = 8 + 1 * n_bytes

         ReDim iodb.cdata(512)
         iodb.cdata(0) = 0

         For n = 0 To n_bytes - 1
            iodb.cdata(n) = Buffer(n)
         Next n

         n_ret_code = Focas1.pmc_wrpmcrng(h_Session, nLength, iodb)

         If (n_ret_code <> Focas1.EW_OK) Then
            sz_Err_Msg = "Error on writing bytes of variable D " & Str(nVar) & " - " & Fanuc_error_codes(n_ret_code)
            'szErrMsg = msg(121) & " " & Str(nVar) & " " & msg(120) & " " & Str(n_ret_code)
            'MsgBox(szErrMsg)
            Return False
         End If

      Else

      End If ' simulazione

      Return True

   End Function
   Public Function F_Write_n_Int_To_PLC(ByVal nVar As Integer, ByVal PMC_area As PMCAreaType,
                                     ByRef Buffer As Short(), ByVal n_ints As Integer) As Boolean

      Dim n As Integer, nLength As Integer
      Dim iodb As Focas1.IODBPMC1 ' per scritture di ints
      '
      sz_Err_Msg = ""
      If Not bSimulation Then ' simulazione ?

         iodb.type_a = PMC_area
         iodb.type_d = N_INT_TYPE
         iodb.datano_s = nVar
         iodb.datano_e = nVar + (2 * n_ints) - 1

         nLength = 8 + (2 * n_ints)

         ReDim iodb.idata(16)
         iodb.idata(0) = 0

         For n = 0 To n_ints - 1
            iodb.idata(n) = Buffer(n)
         Next n

         n_ret_code = Focas1.pmc_wrpmcrng(h_Session, nLength, iodb)

         If (n_ret_code <> Focas1.EW_OK) Then
            sz_Err_Msg = "Error on writing ints of variable D " & Str(nVar) & " - " & Fanuc_error_codes(n_ret_code)
            'szErrMsg = msg(121) & " " & Str(nVar) & " " & msg(120) & " " & Str(n_ret_code)
            'MsgBox(szErrMsg)
            Return False
         End If

      Else

      End If ' simulazione

      Return True

   End Function
    ' ---------------------------------------------------------
    ' scrive una variabile macro (#)  ( comprese le 98xxx)
    ' ---------------------------------------------------------
    Function F_Write_macro(ByVal nVar As Integer, ByVal value As Double) As Boolean

        Dim mcr_val As Long, dec_val As Integer, sz_routine As String = "-"

        sz_Err_Msg = ""
        If Not (bSimulation) Then  ' se non simulazione

            Try
                If nVar >= &H8000 Then   ' if var like 98xxx then use the other write routine .... (   :((  no comment )

                    ReDim values(1)
                    values(0) = value

                    sz_routine = "Focas.cnc_wrmacror2"

                    n_ret_code = Focas1.cnc_wrmacror2(h_Session, nVar, ONE_DATA_ONLY, values)

                Else  ' good ole boys

                    If b_machine_in_inches Then
                        mcr_val = CLng(value * 10000.0#)
                        dec_val = 4 ' 10 e-4
                    Else
                        mcr_val = CLng(value * 1000.0#)
                        dec_val = 3 ' 10 e-3
                    End If

                    sz_routine = "Focas.cnc_wrmacro"

                    n_ret_code = Focas1.cnc_wrmacro(h_Session, nVar, CUSTOM_MACRO_SIZE, mcr_val, dec_val)

                End If ' var > 8000h

                If (n_ret_code <> Focas1.EW_OK) Then '  Fanuc error
                    'Error writing parameter 
                    sz_Err_Msg = "Error on writing # parameter " & Str(nVar) & " in " & sz_routine & " - " & Fanuc_error_codes(n_ret_code)
                    '                    sz_Err_Msg = msg(114) & " in " & sz_routine & " var #" & nVar.ToString & " :   " & Fanuc_error_codes(n_ret_code)
                    '                    Log.Write_and_messagebox(sz_Err_Msg)
                    Return False
                End If '  Fanuc error

            Catch ex As Exception
                sz_Err_Msg = "Error on writing # parameter " & Str(nVar) & " EXC in " & sz_routine & " - " & ex.Message & vbCrLf & ex.StackTrace
                '               sz_Err_Msg = msg(114) & " EXC in " & sz_routine & " var #" & nVar.ToString & " :   " & vbCrLf & ex.Message & vbCrLf & ex.StackTrace
                '               Log.Write_and_messagebox(sz_Err_Msg)
                Return False

            End Try

            Return True

        Else
            Return True ' simulazione
        End If  ' se non simulazione

    End Function

    ' ---------------------------------------------------------
    ' legge una variabile macro (#)
    ' ---------------------------------------------------------
    Function F_Read_macro(ByVal nVar As Integer, ByRef dValue As Double) As Boolean

        Dim ODBM As Focas1.ODBM
        Dim MacroInfo3 As Focas1.IODBMRN3 = Nothing

        Dim sz_routine As String = "-", sz_temp As String = ""

        sz_Err_Msg = ""

        ' se non simulazione
        If Not (bSimulation) Then

            Try
                If nVar >= &H8000 Then   ' if var like 98xxx then use the other read routine .... (   :((  no comment )

                    sz_routine = "Focas.cnc_rdmacror3"

                    '                    If IniRead.b_verbose Then Log.write("F_Read_macro  3 " & values(0).ToString)

                    n_ret_code = Focas1.cnc_rdmacror3(h_Session, nVar, ONE_DATA_ONLY, MacroInfo3)
                    '                    n_ret_code = Focas1.cnc_rdmacror2(h_Session, nVar, ONE_DATA_ONLY, values)

                    If (n_ret_code = Focas1.EW_OK) Then ' no Fanuc error

                        dValue = MacroInfo3.mcr_val

                    Else
                        'Error  reading parameter :
                        sz_Err_Msg = "Error on reading # parameter " & Str(nVar) & " in " & sz_routine & " - " & Fanuc_error_codes(n_ret_code)
                        '                        sz_Err_Msg = msg(112) & " in " & sz_routine & " var # " & nVar.ToString & " : " & Fanuc_error_codes(n_ret_code)
                        '                       Log.Write_and_messagebox(sz_Err_Msg)
                        dValue = 0.0
                        Return False

                    End If ' no Fanuc error

                Else  ' good ole boys

                    ' cnc_rdmacro : read custom macro variable
                    sz_routine = "Focas.cnc_rdmacro"

                    n_ret_code = Focas1.cnc_rdmacro(h_Session, nVar, CUSTOM_MACRO_SIZE, ODBM)

                    If (n_ret_code = Focas1.EW_OK) Then ' no Fanuc error

                        If ODBM.mcr_val = 0 And ODBM.dec_val = -1 Then  ' variabile non definita
                            dValue = 0 '"Null"
                        Else
                            dValue = ODBM.mcr_val * (10 ^ -(ODBM.dec_val))
                        End If
                    Else
                        'Error  reading parameter :
                        sz_Err_Msg = "Error on reading # parameter " & Str(nVar) & " in " & sz_routine & " - " & Fanuc_error_codes(n_ret_code)
                        '                        sz_Err_Msg = (msg(112) & " in " & sz_routine & " var # " & nVar.ToString & " : " & Fanuc_error_codes(n_ret_code))
                        '                       Log.Write_and_messagebox(sz_Err_Msg)
                        dValue = 0.0
                        Return False
                    End If ' no Fanuc error

                End If ' var > 8000h

            Catch ex As Exception
                sz_Err_Msg = "Error on reading # parameter " & Str(nVar) & " EXC in " & sz_routine & " - " & ex.Message & vbCrLf & ex.StackTrace
                '                sz_Err_Msg = msg(112) & " EXC in " & sz_routine & " var #" & nVar.ToString & vbCrLf & ex.Message & vbCrLf & ex.StackTrace
                '               Log.Write_and_messagebox(sz_Err_Msg)
                dValue = 0.0
                Return False
            End Try

            Return True

        Else
            dValue = 0.0
            Return True
        End If ' simulation

    End Function
#End Region

#Region " Alarms"

   ' ---------------------------------------------------------
   ' legge allarmi 
   ' ---------------------------------------------------------
   Public Function F_cnc_alarm() As Long

      Dim l_alarm As Long = 0

      sz_Err_Msg = ""
      If Not bSimulation Then ' simulazione ?

         n_ret_code = Focas1.cnc_alarm2(h_Session, l_alarm)

         If (n_ret_code <> Focas1.EW_OK) Then ' no Fanuc error
            sz_Err_Msg = "Error in F_cnc_alarm " & Str(l_alarm) & " - " & Fanuc_error_codes(n_ret_code)
            'szErrMsg = msg(120) & " " & Str(n_ret_code)
            'MsgBox(szErrMsg)

            Return BAD_RETURN
            Exit Function
         End If ' no Fanuc error

      Else

      End If ' simulazione

      Return l_alarm

   End Function
   '
   ' !!!!! probabilmente non funziona
   '
   Public Function F_get_cnc_alarms(ByVal n_alarm_type As Short) As String

      '        Const Alarm_information_type_1 As Short = 0  ' no message
      Const Alarm_information_type_2 As Short = 1  ' with message

      Const N_MSG = 5

      Dim n_alarm_info_type As Short = Alarm_information_type_2 ' Or Alarm_information_type_1

      '        Dim alarm_info1 As Focas1.ALMINFO_1 = Nothing  ' as defined as default in fwlib32.vb
      Dim alarm_info2 As Focas1.ALMINFO_2 = Nothing ' as defined as default in fwlib32.vb

      Dim n_length As Short

      Dim sz_return As String

      sz_Err_Msg = ""
      sz_return = ""

      If Not bSimulation Then ' simulazione ?


         '       If n_alarm_info_type = Alarm_information_type_1 Then
         '          n_length = 4 * N_MSG + 2                ' per 16/18/21 ; 16/18/21i ; 0i A/B/C ; Power mate i
         '          n_length = 8 * N_MSG + 4                ' per 30i ; Oi D/F ; PMi-A
         '          n_ret_code = Focas1.cnc_rdalminfo(h_Session, Alarm_information_type_1, n_alarm_type, n_length, alarm_info1)
         '        Else
         '          n_length = 38 * N_MSG + 2                ' per 16/18/21 ; 16/18/21i ; 0i A/B/C ; Power mate i

         n_length = 40 * N_MSG + 4                ' per 30i ; Oi D/F ; PMi-A
         n_ret_code = Focas1.cnc_rdalminfo(h_Session, Alarm_information_type_2, n_alarm_type, n_length, alarm_info2)

         '       End If


         If (n_ret_code <> Focas1.EW_OK) Then
            sz_Err_Msg = "Error in F_get_cnc_alarms " + Str(n_alarm_type) & " - " & Fanuc_error_codes(n_ret_code)
            '           szErrMsg = msg(120) & " " & Str(n_ret_code)
            '          MsgBox(szErrMsg)
            Return BAD_RETURN.ToString
         End If


         With alarm_info2.msg1
            If .axis <> -1 Then
               sz_return = sz_return & " Alarm " & .alm_no.ToString & " - " & .alm_msg.Substring(0, .msg_len)
            End If
         End With

         With alarm_info2.msg2
            If .axis <> -1 Then
               sz_return = sz_return & Environment.NewLine
               sz_return = sz_return & " Alarm " & .alm_no.ToString & " - " & .alm_msg.Substring(0, .msg_len)
            End If
         End With

         With alarm_info2.msg3
            If .axis <> -1 Then
               sz_return = sz_return & Environment.NewLine
               sz_return = sz_return & " Alarm " & .alm_no.ToString & " - " & .alm_msg.Substring(0, .msg_len)
            End If
         End With

         With alarm_info2.msg4
            If .axis <> -1 Then
               sz_return = sz_return & Environment.NewLine
               sz_return = sz_return & " Alarm " & .alm_no.ToString & " - " & .alm_msg.Substring(0, .msg_len)
            End If
         End With

         With alarm_info2.msg5
            If .axis <> -1 Then
               sz_return = sz_return & Environment.NewLine
               sz_return = sz_return & " Alarm " & .alm_no.ToString & " - " & .alm_msg.Substring(0, .msg_len)
            End If
         End With
      Else

      End If ' simulazione

      Return sz_return

   End Function

   Public Function F_get_cnc_alarms3() As Short

      Dim n_AlmMsgCount As Short = 0
      Dim odbAlm As Focas1.ODBALMMSG2 = Nothing  ' defaults to 10 messages in fwlib32.vb

      sz_Err_Msg = ""

      If Not bSimulation Then ' simulazione ?

         n_AlmMsgCount = MAX_CNC_ALM_MSG

         odbAlm.msg1.dummy = 0

         n_ret_code = Focas1.cnc_rdalmmsg2(h_Session, ALL_ALARM_TYPE, n_AlmMsgCount, odbAlm)

         If (n_ret_code <> Focas1.EW_OK) Then
            sz_Err_Msg = "Error in F_get_cnc_alarms3 " & " - " & Fanuc_error_codes(n_ret_code)
            'szErrMsg = msg(120) & " " & Str(n_ret_code)
            'MsgBox(szErrMsg)
            Return (BAD_RETURN_SH)
         End If

         AlarmMessageCount = n_AlmMsgCount

         AlarmMessage(0) = odbAlm.msg1.alm_msg
         AlarmMessage(1) = odbAlm.msg2.alm_msg
         AlarmMessage(2) = odbAlm.msg3.alm_msg
         AlarmMessage(3) = odbAlm.msg4.alm_msg
         AlarmMessage(4) = odbAlm.msg5.alm_msg
         AlarmMessage(5) = odbAlm.msg6.alm_msg
         AlarmMessage(6) = odbAlm.msg7.alm_msg
         AlarmMessage(7) = odbAlm.msg8.alm_msg
         AlarmMessage(8) = odbAlm.msg9.alm_msg
         AlarmMessage(9) = odbAlm.msg10.alm_msg

         AlarmNumber(0) = odbAlm.msg1.alm_no
         AlarmNumber(1) = odbAlm.msg2.alm_no
         AlarmNumber(2) = odbAlm.msg3.alm_no
         AlarmNumber(3) = odbAlm.msg4.alm_no
         AlarmNumber(4) = odbAlm.msg5.alm_no
         AlarmNumber(5) = odbAlm.msg6.alm_no
         AlarmNumber(6) = odbAlm.msg7.alm_no
         AlarmNumber(7) = odbAlm.msg8.alm_no
         AlarmNumber(8) = odbAlm.msg9.alm_no
         AlarmNumber(9) = odbAlm.msg10.alm_no
      Else

      End If ' simulazione

      Return (n_AlmMsgCount)

   End Function

   Public Function F_get_operator_messages() As Short

      Dim n_MsgCount As Short = 0
      Dim opMsg As Focas1.OPMSG3 = Nothing  ' defaults to 5 messages in fwlib32.vb

      sz_Err_Msg = ""
      If Not bSimulation Then ' simulazione ?
         Try

            '        n_MsgCount = 5          ' 16/18/21, 16i/18i/21i, 0i-A/B/C
            '        n_MsgCount = 17         ' 30i, 0i-D/F, PMi-A
            n_MsgCount = 5         ' 30i, 0i-D/F, PMi-A  NO COMMENT

            n_ret_code = Focas1.cnc_rdopmsg3(h_Session, ALL_OP_MSG_TYPE, n_MsgCount, opMsg)

            '        Const MAX_OPERATOR_ALM_MSG As Short = 5 ' max number of messages

            If (n_ret_code <> Focas1.EW_OK) Then
               sz_Err_Msg = "Error in F_get_operator_messages " & " - " & Fanuc_error_codes(n_ret_code)
               'szErrMsg = msg(120) & " " & Str(n_ret_code)
               'MsgBox(szErrMsg)
               Return (BAD_RETURN_SH)
            End If

            'OperatorMessageCount = n_MsgCount
            OperatorMessageCount = 0

            OperatorMessage(0) = opMsg.msg1.data
            If Not String.IsNullOrEmpty(OperatorMessage(0)) Then
               OperatorMessageCount += 1
            End If
            OperatorMsgNumber(0) = opMsg.msg1.datano

            OperatorMessage(1) = opMsg.msg2.data
            If Not String.IsNullOrEmpty(OperatorMessage(1)) Then
               OperatorMessageCount += 1
            End If
            OperatorMsgNumber(1) = opMsg.msg2.datano

            OperatorMessage(2) = opMsg.msg3.data
            If Not String.IsNullOrEmpty(OperatorMessage(2)) Then
               OperatorMessageCount += 1
            End If
            OperatorMsgNumber(2) = opMsg.msg3.datano

            OperatorMessage(3) = opMsg.msg4.data
            If Not String.IsNullOrEmpty(OperatorMessage(3)) Then
               OperatorMessageCount += 1
            End If
            OperatorMsgNumber(3) = opMsg.msg4.datano

            OperatorMessage(4) = opMsg.msg5.data
            If Not String.IsNullOrEmpty(OperatorMessage(4)) Then
               OperatorMessageCount += 1
            End If
            OperatorMsgNumber(4) = opMsg.msg5.datano

            n_MsgCount = OperatorMessageCount
         Catch ex As Exception
            sz_Err_Msg = "Error in F_get_operator_messages " & " - " & ex.Message
            Return (BAD_RETURN_SH)

         End Try

      Else

      End If ' simulazione

      Return (n_MsgCount)

   End Function


   Public Function F_get_PLC_messages() As Short


      Dim n_MsgCount As Short = 10
      Dim odbpmcalm As Focas1.ODBPMCALM = Nothing  ' defaults to 5 messages in fwlib32.vb

      Dim n_start As Short = 1
      Dim n_more_msg As Short, n_total_msg As Short = 0
      Dim b_end As Boolean = False

      lst_plc_messages.Clear()

      sz_Err_Msg = ""
      If Not bSimulation Then ' simulazione ?
         Try
            While Not b_end

               n_ret_code = Focas1.pmc_rdalmmsg(h_Session, n_start, n_MsgCount, n_more_msg, odbpmcalm)
               If (n_ret_code <> Focas1.EW_OK) Then
                  sz_Err_Msg = "Error in F_get_PLC_messages " & " - " & Fanuc_error_codes(n_ret_code)

                  Return (BAD_RETURN_SH)
               End If

               If n_MsgCount > 0 Then lst_plc_messages.Add(odbpmcalm.msg1.almmsg)
               If n_MsgCount > 1 Then lst_plc_messages.Add(odbpmcalm.msg2.almmsg)
               If n_MsgCount > 2 Then lst_plc_messages.Add(odbpmcalm.msg3.almmsg)
               If n_MsgCount > 3 Then lst_plc_messages.Add(odbpmcalm.msg4.almmsg)
               If n_MsgCount > 4 Then lst_plc_messages.Add(odbpmcalm.msg5.almmsg)
               If n_MsgCount > 5 Then lst_plc_messages.Add(odbpmcalm.msg6.almmsg)
               If n_MsgCount > 6 Then lst_plc_messages.Add(odbpmcalm.msg7.almmsg)
               If n_MsgCount > 7 Then lst_plc_messages.Add(odbpmcalm.msg8.almmsg)
               If n_MsgCount > 8 Then lst_plc_messages.Add(odbpmcalm.msg9.almmsg)
               If n_MsgCount > 9 Then lst_plc_messages.Add(odbpmcalm.msg10.almmsg)

               If n_more_msg < 1 Then b_end = True
               n_total_msg = n_total_msg + n_MsgCount

            End While

         Catch ex As Exception
            sz_Err_Msg = "Error in F_get_PLC_messages " & " - " & ex.Message
            Return (BAD_RETURN_SH)
         End Try

      End If ' simulazione

      Return (n_total_msg)



   End Function

#End Region

#Region " Download/upload"

   Private Const MAX_PNC_PATH_LEN As Short = 212
   Private Const PATH_FOREGROUND As Short = 1
   Private Const PATH_BACKGROUND As Short = 2

   Private sz_Nc_cur_path As String = ""

   Function Send_file_to_nc(ByVal szFileToSend As String, ByVal szDirCn As String, ByVal szNameOnNc As String) As Boolean

      Dim szNamePrgCopy As String
      Dim szProgramDel As String = szDirCn & "\" & szNameOnNc
      Dim b_ret As Boolean = False

      If File.Exists(szFileToSend) Then

         szNamePrgCopy = InserisciNome(szFileToSend, szNameOnNc)  ' correct name inserting for Fanuc 30 series       Dim szProgramDel As String = szDirCn & "\" & szNameOnNc

         If szDirCn <> "" Then
            szProgramDel = szDirCn & "\" & szNameOnNc
         Else
            szProgramDel = szNameOnNc
         End If

         b_ret = F_Delete_Prg(szProgramDel)

         If (b_ret) Then b_ret = F_Send_Prg(szNamePrgCopy, szDirCn)

      End If

      Return b_ret

   End Function

   ' ---------------------------------------------------------
   ' Invia un programma al CN
   ' ---------------------------------------------------------
   Public Function F_Send_Prg(ByVal szFileName As String, ByVal szDirWork As String) As Boolean

      Dim nFile As Integer
      Dim szMaxiStringa As String
      Dim dLenMaxiStringa As Long
      Dim szLine As String
      Dim bError As Boolean, b_ret As Boolean

      Dim l_prg_file_size As Long, l_num_bytes_sent As Long

      b_ret = True
      bError = False
      sz_Err_Msg = ""

      szDirWork = szDirWork.Replace("\", "/")

      If Not szDirWork.Contains("/") Then szDirWork = sz_Nc_cur_path


      If Not bSimulation Then               ' se non simulazione

         If (System.IO.File.Exists(szFileName)) Then                     ' verifico che il file esista

            n_ret_code = Focas1.cnc_dwnstart4(h_Session, 0, szDirWork)  ' start download

            If (n_ret_code = Focas1.EW_OK) Then                         ' cnc_dwnstart4 tutto Ok ?

               ' leggo tutto il file in una maxi stringa 
               nFile = FreeFile()
               FileOpen(nFile, szFileName, OpenMode.Input)

               szMaxiStringa = ""

               While Not EOF(nFile)
                  szLine = LineInput(nFile)                           ' leggo linea
                  szMaxiStringa = szMaxiStringa & vbCrLf & szLine     ' la scrivo nella maxi stringa
               End While

               szMaxiStringa = szMaxiStringa & vbCrLf
               dLenMaxiStringa = Len(szMaxiStringa)            ' lunghezza stringa che contiene l' intero programma....

               l_prg_file_size = dLenMaxiStringa
               l_num_bytes_sent = 0

               FileClose(nFile)                                ' chiudo file

               ' ciclo scrittura (manda blocchi di n caratteri)

               While ((dLenMaxiStringa > 0) And (bError = False))
                  ' mando (dLenMaxiStringa bytes e mi dice quanti ne ho mandati)
                  n_ret_code = Focas1.cnc_download4(h_Session, dLenMaxiStringa, szMaxiStringa)

                  If (n_ret_code = Focas1.EW_BUFFER) Then     '  EW_BUFFER ? 

                     n_ret_code = Focas1.EW_OK               ' riprovo al prossimo giro

                  ElseIf (n_ret_code = Focas1.EW_OK) Then     ' cnc_download4 ok ?

                     szMaxiStringa = Mid(szMaxiStringa, dLenMaxiStringa + 1) ' aggiusto stringa (tolgo caratteri mandati)

                     l_num_bytes_sent = l_num_bytes_sent + dLenMaxiStringa
                     dLenMaxiStringa = Len(szMaxiStringa)                    ' ricalcolo lunghezza

                  Else ' errore .....

                     ' MsgBox(msg(128) & " - " & Fanuc_error_codes(n_ret_code), MsgBoxStyle.Critical, "F_send_prg") ' "Problem ending trasmission"
                     sz_Err_Msg = "Error in F_send_prg - cnc_download4 - " & Fanuc_error_codes(n_ret_code)

                     Call Focas1.cnc_dwnend4(h_Session)
                     b_ret = False
                     bError = True

                  End If  ' cnc_download4 ok
                  '
               End While

               n_ret_code = Focas1.cnc_dwnend4(h_Session)  ' Chiudo tx

            Else                                         '
               ' msgBox(msg(127) & " - " & Fanuc_error_codes(n_ret_code), MsgBoxStyle.Critical, "F_send_prg") '                     MsgBox("Problem starting trasmission")
               sz_Err_Msg = "Error in F_send_prg - cnc_dwnstart4 - " & Fanuc_error_codes(n_ret_code)

               b_ret = False

            End If   ' cnc_dwnstart4 tutto Ok

         Else                    ' File Da spedire non trovato
            sz_Err_Msg = "Error in F_send_prg - the file : " & szFileName & "do not exist"
            '               MsgBox(msg(108) & " : " & szFileName & "  " & msg(109))
            b_ret = False
         End If

      Else

      End If ' simulation

      Return b_ret

   End Function
   '
   ' Ricevi programma da CN
   '
   Public Function F_Receive_Prg(ByVal szFileName As String, ByVal sz_NC_programname As String) As Boolean

      ' sz_NC_programname can be:

      ' File name only 	:  	"O1234"
      ' Folder name       :  	"//CNC_MEM/USER/PATH1/"
      ' Path + file name 	:  	"//CNC_MEM/USER/PATH1/O1234"

      Dim b_exit As Boolean = False
      Dim sz_temp As String = ""
      Dim sz_Maxi_String As String = ""
      Dim n_read_length As Short

      If Not bSimulation Then               ' se non simulazione


         If Not sz_NC_programname.Contains("/") Then sz_NC_programname = sz_Nc_cur_path & sz_NC_programname


         ' start uploading NC program 4
         n_ret_code = Focas1.cnc_upstart4(h_Session, 0, sz_NC_programname)

         If (n_ret_code <> Focas1.EW_OK) Then
            sz_Err_Msg = "Error in cnc_upstart4 - file : " & sz_NC_programname & " - " & Fanuc_error_codes(n_ret_code)
            Return False
         End If

         Try

            ' ciclo lettura (manda blocchi di n caratteri)

            While (b_exit = False)

               System.Threading.Thread.Sleep(50)

               n_read_length = 1024   ' chiedo n_read_length bytes e mi dice quanti ne ho mandati
               n_ret_code = Focas1.cnc_upload4(h_Session, n_read_length, sz_temp)

               If (n_ret_code = Focas1.EW_BUFFER) Then     '  EW_BUFFER ? 

                  n_ret_code = Focas1.EW_OK               ' riprovo al prossimo giro

               ElseIf (n_ret_code = Focas1.EW_OK) Then     ' cnc_upload4 ok ?

                  If sz_temp.Contains(Chr(0)) Then
                     sz_temp = sz_temp.Replace(Chr(0), "")
                  End If

                  If sz_temp.StartsWith("%") Then
                     sz_temp = sz_temp.Replace("%", "")
                  End If

                  If sz_temp.EndsWith("%") Then
                     sz_temp = sz_temp.Replace("%", "")
                     b_exit = True
                  End If

                  sz_Maxi_String = sz_Maxi_String & sz_temp


               Else ' errore .....
                  ' MsgBox(msg(128) & " - " & Fanuc_error_codes(n_ret_code), MsgBoxStyle.Critical, "F_send_prg") ' "Problem ending trasmission"
                  sz_Err_Msg = "Error in F_Receive_Prg - cnc_upload4 - " & Fanuc_error_codes(n_ret_code)

                  Call Focas1.cnc_upend4(h_Session)

                  Return False

               End If  ' cnc_upload4 ok
               '
            End While

         Catch ex As Exception
            MsgBox("Error 791 in F_Receive_Prg" & ex.Message)

         End Try

         n_ret_code = Focas1.cnc_dwnend4(h_Session)  ' Chiudo tx
         If (n_ret_code = Focas1.EW_OK) Then     ' 

            Dim Writer As StreamWriter

            Try
               Writer = New StreamWriter(szFileName, False)

               Writer.WriteLine(sz_Maxi_String)

               Writer.Flush()
               Writer.Close()

            Catch ex As Exception
               MsgBox("Error 792 in F_Receive_Prg" & ex.Message)
               Return False
            End Try

         Else
            sz_Err_Msg = "Error 793 in cnc_dwnend4 - file : " & sz_NC_programname & " - " & Fanuc_error_codes(n_ret_code)
            Return False
         End If

      End If ' non simulazione

      Return True

   End Function

   ' ---------------------------------------------------------
   ' Cancella programma su CN
   ' ---------------------------------------------------------
   Function F_Delete_Prg(ByVal szNomePrg As String) As Boolean

      Dim b_ret As Boolean

      ' barre invertite
      szNomePrg = szNomePrg.Replace("\", "/")

      If Not szNomePrg.Contains("/") Then szNomePrg = sz_Nc_cur_path & szNomePrg


      b_ret = True
      sz_Err_Msg = ""

      ' se non simulazione
      If Not bSimulation Then

         n_ret_code = Focas1.cnc_pdf_del(h_Session, szNomePrg)

         If (n_ret_code = Focas1.EW_OK) Then Return True

         If fanuc_error_file_not_found(n_ret_code) Then Return True ' if file not found error... no problem

         ' casi di errore
         If (n_ret_code = Focas1.EW_PROT) Then
            sz_Err_Msg = "Error in F_Delete_Prg - file protected : " & szNomePrg
            '                MsgBox(msg(110) & " : " & szNomePrg)
            b_ret = False

         ElseIf (n_ret_code = Focas1.EW_BUSY) Then
            sz_Err_Msg = "Error in F_Delete_Prg - file busy : " & szNomePrg
            '                MsgBox(msg(111) & " : " & szNomePrg)
            b_ret = False

         ElseIf (n_ret_code = Focas1.EW_REJECT) Then
            sz_Err_Msg = "Error in F_Delete_Prg - file reject : " & szNomePrg
            '                MsgBox(msg(112) & " : " & szNomePrg)
            b_ret = False

         Else
            sz_Err_Msg = "Error in F_Delete_Prg - file  : " & szNomePrg & " - " & Fanuc_error_codes(n_ret_code)
            b_ret = False
         End If

      End If ' simulation

      Return b_ret

   End Function

   ' ---------------------------------------------------------
   ' Ritorna path corrente su CN
   ' ---------------------------------------------------------
   Function F_Get_current_NC_dir(ByRef sz_NC_current_path As String) As Integer

      Dim ch_temp As Char()

      sz_Err_Msg = ""

      ' se non simulazione
      If Not bSimulation Then

         ReDim ch_temp(MAX_PNC_PATH_LEN)

         n_ret_code = Focas1.cnc_rdpdf_curdir(h_Session, PATH_FOREGROUND, ch_temp)

         If (n_ret_code = Focas1.EW_OK) Then

            sz_NC_current_path = Get_null_terminated_string(ch_temp)


            If (sz_NC_current_path.Length > 0) And (Not sz_NC_current_path.EndsWith("/")) Then
               sz_NC_current_path = sz_NC_current_path & "/"   ' convenzione Fanuc per path nname : deve terminare con /
            End If

            sz_Nc_cur_path = sz_NC_current_path

            Return n_ret_code

         Else
            sz_Err_Msg = "Error in F_Get_current_NC_dir - file  : " & Fanuc_error_codes(n_ret_code)
            Return n_ret_code
         End If

      End If ' simulation

      Return Focas1.EW_OK

   End Function

   '------------------------------------
   ' Cambia nome interno del CN in <Nomesend>
   '------------------------------------
   Private Function InserisciNome(ByVal szFileName As String, ByVal NomeSend As String) As String
      Dim szLine As String
      Dim nFiler As Integer
      Dim nFilew As Integer
      Dim nLen As Integer

      Dim szFileProgramma As String

      nLen = InStrRev(szFileName, "\")

      'NomeOk = Mid(szFileName, nLen + 1)              ' filename ( senza "\" 

      szFileProgramma = Mid(szFileName, 1, nLen)      ' path ( fino a "\" inclusa )

      szFileProgramma = szFileProgramma & "Temp.txt"

      ' apertura file in input 
      nFiler = FreeFile()
      FileOpen(nFiler, szFileName, OpenMode.Input)

      ' apertura file in output 
      nFilew = FreeFile()
      FileOpen(nFilew, szFileProgramma, OpenMode.Output)

      '        PrintLine(nFilew, "%" & vbLf & "<" & NomeSend & ">") ' !!!!!!!! da spostare
      PrintLine(nFilew, vbLf & "<" & NomeSend & ">") ' !!

      'trascrivo file tranne prima linea
      While (Not EOF(nFiler))

         ' leggo linea  
         szLine = LineInput(nFiler)

         ' leva linee con % e <e cambia M30 in M99

         ' dopo il % serve il nome del programma

         If ((InStr(szLine, "%") > 0)) Then   'leva %
            '                PrintLine(nFilew, szLine)
         ElseIf ((InStr(szLine, "<") > 0)) Then   'leva <....
            'PrintLine(nFilew, "<" & NomeSend & ">")
            ' qq
         ElseIf (Mid(szLine, 1, 1) = "O") Then   ' leva le righe Oxxxxx
            'qq
            'ElseIf ((InStr(szLine, "M30") > 0)) Then  ' cambia M30 in M99
            '   PrintLine(nFilew, "M99")
         Else
            PrintLine(nFilew, szLine)
         End If

      End While

      PrintLine(nFilew, "%") ' !!

      ' chiusura files
      FileClose(nFiler)
      FileClose(nFilew)


      Return szFileProgramma

   End Function

   Private Function Get_null_terminated_string(cha As Char()) As String

      Dim sz_ret As String = ""

      For i As Short = 0 To MAX_PNC_PATH_LEN - 1

         If cha(i) <> Chr(0) Then
            sz_ret = sz_ret & cha(i)
         Else
            Exit For
         End If

      Next

      Return sz_ret

   End Function

#End Region

#Region " Positions"
   ' ---------------------------------------------------------
   ' NC read absolute axis position 
   ' ---------------------------------------------------------
   Function F_read_position_ABS() As Boolean

      Dim odbaxis As Focas1.ODBAXIS = Nothing ' defaults to 8 in fwlib32.vb
      Dim n_size As Short

      sz_Err_Msg = ""

      n_size = 4 + 4 * 32

      n_ret_code = Focas1.cnc_absolute2(h_Session, ALL_AXES, n_size, odbaxis)

      If n_ret_code = Focas1.EW_OK Then

         For n As Short = 0 To Focas1.MAX_AXIS - 1

            l_pos_values(n) = odbaxis.data(n)

         Next

         Return True
      Else
         sz_Err_Msg = "Error in F_read_position_ABS : " & Fanuc_error_codes(n_ret_code)
         Return False
      End If

   End Function

   ' ---------------------------------------------------------
   ' NC read machine axis position 
   ' ---------------------------------------------------------
   Function F_read_position_MACH() As Boolean

      Dim odbaxis As Focas1.ODBAXIS = Nothing ' defaults to 8 in fwlib32.vb
      Dim n_size As Short

      sz_Err_Msg = ""

      n_size = 4 + 4 * 32

      n_ret_code = Focas1.cnc_machine(h_Session, ALL_AXES, n_size, odbaxis)

      If n_ret_code = Focas1.EW_OK Then

         For n As Short = 0 To Focas1.MAX_AXIS - 1

            l_pos_values(n) = odbaxis.data(n)

         Next

         Return True
      Else
         sz_Err_Msg = "Error in F_read_position_MACH : " & Fanuc_error_codes(n_ret_code)
         Return False
      End If

   End Function

   ' ---------------------------------------------------------
   ' NC read delta axis position 
   ' ---------------------------------------------------------
   Function F_read_position_DELTA() As Boolean

      Dim odbaxis As Focas1.ODBAXIS = Nothing ' defaults to 8 in fwlib32.vb
      Dim n_size As Short

      sz_Err_Msg = ""

      n_size = 4 + 4 * 32

      n_ret_code = Focas1.cnc_distance(h_Session, ALL_AXES, n_size, odbaxis)

      If n_ret_code = Focas1.EW_OK Then

         For n As Short = 0 To Focas1.MAX_AXIS - 1

            l_delta_values(n) = odbaxis.data(n)

         Next

         Return True
      Else
         sz_Err_Msg = "Error in F_read_position_DELTA : " & Fanuc_error_codes(n_ret_code)
         Return False
      End If

   End Function
#End Region


   ' ---------------------------------------------------------
   ' selezione programma su CN
   ' ---------------------------------------------------------
   Function F_Select_Prg(ByVal szNomePrg As String) As Boolean

      sz_Err_Msg = ""
      If Not bSimulation Then
            ' barre invertite
            szNomePrg = szNomePrg.Replace("\", "/")
            'If Not szNomePrg.StartsWith("/") Then szNomePrg = "/" & szNomePrg

            If Not szNomePrg.Contains("/") Then szNomePrg = sz_Nc_cur_path & szNomePrg
         n_ret_code = Focas1.cnc_pdf_slctmain(h_Session, szNomePrg)     ' select program file

         If n_ret_code = Focas1.EW_OK Then
            Return True
         Else
            sz_Err_Msg = "Error in F_Select_Prg : " & szNomePrg & Environment.NewLine & Fanuc_error_codes(n_ret_code)
            Return False
         End If

      End If ' simulation

      Return True

   End Function

   ' ---------------------------------------------------------
   ' reset CN
   ' ---------------------------------------------------------
   Function F_reset() As Boolean

      sz_Err_Msg = ""
      If Not bSimulation Then

         'n_ret_code = Focas1.cnc_reset(h_Session)

         n_ret_code = Focas1.cnc_reset2(h_Session)

         If n_ret_code = Focas1.EW_OK Then
            Return True
         Else
            sz_Err_Msg = "Error in F_reset : " & Fanuc_error_codes(n_ret_code)
            Return False
         End If
      End If ' simulation

      Return True

   End Function

   ' ---------------------------------------------------------
   ' Cycle Start
   ' ---------------------------------------------------------
   Function F_cycle_start() As Boolean

      sz_Err_Msg = ""
      If Not bSimulation Then

         n_ret_code = Focas1.cnc_start(h_Session)

         '        n_ret_code = Focas1.cnc_reset2(h_Session)

         If n_ret_code = Focas1.EW_OK Then
            Return True
         Else
            sz_Err_Msg = "Error in F_cycle_start : " & Fanuc_error_codes(n_ret_code)
            Return False
         End If
      End If ' simulation

      Return True

   End Function

   ' ---------------------------------------------------------
   ' NC status 
   ' ---------------------------------------------------------
   Function F_NC_status(ByRef n_status As Short) As Boolean
      ' 
      ' returns
      '
      ' 0	: MDI
1:      ' 1 : MEMory
2:      ' 2 : ***
3:      ' 3 : EDIT
4:      ' 4 : HaNDle
5:      ' 5 : JOG
6:      ' 6 : Teach in JOG
7:      ' 7 : Teach in HaNDle
8:      ' 8 : INC·feed
9:      ' 9 : REFerence
10:     '10 : ReMoTe
      '
      Dim odbstat As Focas1.ODBST

      '
      'Dim odbstat2 As Focas1.ODBST2
      ' !!!!!!!!!!!!!!!!!!!!!!        n_ret_code = Focas1.cnc_statinfo2(h_Session, odbstat2)

      sz_Err_Msg = ""
      If Not bSimulation Then

         n_ret_code = Focas1.cnc_statinfo(h_Session, odbstat)


         If n_ret_code = Focas1.EW_OK Then

            '                n_status = odbstat2.aut

            n_status = odbstat.aut

            Return True
         Else
            sz_Err_Msg = "Error in F_NC_status : " & Fanuc_error_codes(n_ret_code)
            Return False
         End If
      End If ' simulation

      Return True

   End Function

   ' ---------------------------------------------------------
   ' NC system info
   ' ---------------------------------------------------------
   Function F_sys_info() As Boolean

      Dim odbsys As Focas1.ODBSYS = Nothing

      sz_Err_Msg = ""
      If Not bSimulation Then

         n_ret_code = Focas1.cnc_sysinfo(h_Session, odbsys)

         If n_ret_code = Focas1.EW_OK Then

            sz_NC_type = odbsys.cnc_type

            Return True
         Else
            sz_Err_Msg = "Error in F_sys_info : " & Fanuc_error_codes(n_ret_code)
            Return False
         End If
      End If ' simulation

      Return True

   End Function

   ' ---------------------------------------------------------
   ' MDI
   ' ---------------------------------------------------------
   Function F_MDI_write_program(sz_MDI_command As String) As Boolean

      Dim sz_MDI_program As String = ""

      sz_Err_Msg = ""
      If Not bSimulation Then

         ' Nicola: 10/05/2024

         Dim sItems As String() = sz_MDI_command.Split(";")
         Dim sNew_MDI_program As String = ""
         For Each sItem As String In sItems
            sNew_MDI_program &= sItem & vbLf
         Next
         sNew_MDI_program &= "%"

         sz_MDI_program = sNew_MDI_program

         ' Nicola: 29/03/2023

         If Not sz_MDI_program.StartsWith(vbLf) Then sz_MDI_program = vbLf & sz_MDI_program
         If Not sz_MDI_program.EndsWith(";") Then sz_MDI_program &= ";"
         If Not sz_MDI_program.EndsWith(vbLf) Then sz_MDI_program &= vbLf
         If Not sz_MDI_program.EndsWith("%") Then sz_MDI_program &= "%"

         n_ret_code = Focas1.cnc_wrmdiprog(h_Session, sz_MDI_program.Length, sz_MDI_program)

         If n_ret_code = Focas1.EW_OK Then
            Return True
         Else
            sz_Err_Msg = "Error in F_MDI_write_program : " & Fanuc_error_codes(n_ret_code)
            Return False
         End If

      End If ' simulation

      Return True

   End Function


End Module