using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;
using GcDevicePc.IniParam;

namespace GcDevicePc.Common
{
    class GCModbusSlave
    {
        [UnmanagedFunctionPointer(CallingConvention.Cdecl)]
        public unsafe delegate ushort SlaveReadHoldingRegister(ushort address);
        [UnmanagedFunctionPointer(CallingConvention.Cdecl)]
        public unsafe delegate void SlaveWriteHoldingRegister(ushort address, ushort value);

        [UnmanagedFunctionPointer(CallingConvention.Cdecl)]
        public unsafe delegate ushort SlaveReadCoilsRegister(ushort address);
        [UnmanagedFunctionPointer(CallingConvention.Cdecl)]
        public unsafe delegate void SlaveWriteCoilsRegister(ushort address, ushort value);

        [DllImport(@"LibModbus.dll", EntryPoint = "fnLibModbusSlaveInit", CharSet = CharSet.Unicode)]
        public static extern uint fnLibModbusSlaveInit();

        [DllImport(@"LibModbus.dll", EntryPoint = "fnLibModbusSlaveHoldingRegister", CallingConvention = CallingConvention.Cdecl)]
        public static extern void fnLibModbusSlaveHoldingRegister(System.UInt32 handle, SlaveReadHoldingRegister callslavereadholdingreg, SlaveWriteHoldingRegister callslavewirteholdingreg, ushort startAddr, ushort NReg);

        [DllImport(@"LibModbus.dll", EntryPoint = "fnLibModbusSlaveCoilsRegister",  CallingConvention = CallingConvention.Cdecl)]
        public static extern void fnLibModbusSlaveCoilsRegister(System.UInt32 handle, SlaveReadCoilsRegister callslavereadcoilsreg, SlaveWriteCoilsRegister callslavewirtecoilsreg, ushort startAddr, ushort NReg);

        [DllImport(@"LibModbus.dll", EntryPoint = "fnLibModbusSlaveClose")]
        public static extern uint fnLibModbusSlaveClose(uint handle);

        private uint hModbusHandle;

        public GCModbusSlave()
        {
            try
            {
                this.hModbusHandle = fnLibModbusSlaveInit();
            }
            catch
            {

            }
            
        }

        ~GCModbusSlave()
        {
            try
            {
                fnLibModbusSlaveClose(hModbusHandle);
            }catch
            {

            }
        }

        public uint CModbusSlaveClose()
        {
            uint ret = 0;
            try
            {
                ret = fnLibModbusSlaveClose(hModbusHandle);
            }
            catch
            {

            }
            
            return ret; 
        }


        public void CModbusSlaveInit(ushort hstartaddr, ushort hnreg, ushort cstartaddr, ushort cnreg)
        {
            setHoldingRegisterFunc(hstartaddr, hnreg);
            setCoilsRegisterFunc(cstartaddr, cnreg);
        }

        SlaveReadHoldingRegister MySlaveReadHoldingRegister;
        SlaveWriteHoldingRegister MySlaveWriteHoldingRegister;
        
        public void setHoldingRegisterFunc( ushort startaddr, ushort nreg)
        {
            MySlaveReadHoldingRegister = new SlaveReadHoldingRegister(slavereadhreg);
            MySlaveWriteHoldingRegister = new SlaveWriteHoldingRegister(slavewirtehreg);
            fnLibModbusSlaveHoldingRegister(hModbusHandle, MySlaveReadHoldingRegister, MySlaveWriteHoldingRegister, startaddr, nreg);
        }

        static ushort slavereadhreg(ushort address)
        {
            ushort value = 0;
            ushort signalddress = 17;
            ushort baseaddress = 23;
            address = (ushort)(address - 1);
            int listnum = SharedSpace.Data.listValue.Count;
            if (address >= 17)
            {
                ushort[] s = new ushort[2];
                float[] f = new float[2];
                if (address >= 17 && address <= 22)
                {
                    if (address == 17 || address == 18)
                        f[0] = float.Parse(globaldata.m_dpbuffer.ShowList.showDet.fDetValue.ToString("0.000"));
                    if (address == 19 || address == 20)
                        f[0] = float.Parse(globaldata.m_dpbuffer.ShowList.showDet.iDetValue.ToString("0.000"));
                    if (address == 21 || address == 22)
                        f[0] = float.Parse(globaldata.m_dpbuffer.ShowList.showDet.bDetValue.ToString("0.000"));
                    Buffer.BlockCopy(f, 2, s, 0, 2);
                    Buffer.BlockCopy(f, 0, s, 2, 2);
                    value = s[(address - signalddress) % 2];
                }
                else if ( address >= 23 && listnum > 0)
                {
                    int readnum = (address - baseaddress) / 2;
                    if (readnum <= listnum - 1)
                    {
                        f[0] = float.Parse(SharedSpace.Data.listValue[readnum].vale.ToString());
                        Buffer.BlockCopy(f, 2, s, 0, 2);
                        Buffer.BlockCopy(f, 0, s, 2, 2);
                        value = s[(address - baseaddress) % 2];
                    }
                    else
                    {
                        value = 0;
                    }
                   
                }
                else
                {
                    value = 0;
                }
            }

            if (address >= 2 && address < 20)
            {
                switch (address)
                {
                    case 2:
                        {
                            value = (ushort)SharedSpace.Data.typesint;
                        }
                        break;
                    case 3:
                        {
                            value = SharedSpace.Data.change == true ? (ushort)1 : (ushort)0;
                        }
                        break;
                    case 4:
                        {
                            value = globaldata.m_hmibuffer.gcinfo.HMIMac[0];
                        }
                        break;
                    case 5:
                        {
                            value = globaldata.m_hmibuffer.gcinfo.HMIMac[1];
                        }
                        break;
                    case 6:
                        {
                            value = globaldata.m_hmibuffer.gcinfo.HMIMac[2];
                        }
                        break;
                    case 7: //设备联机状态
                        {
                            value = (ushort)(globaldata.m_hmibuffer.gcinfo.hmioffline ? 1 : 0);
                        }
                        break;
                    case 8: //HMI状态
                        {
                            value = globaldata.m_hmibuffer.gcinfo.methodstatus;
                        }
                        break;
                    case 9: //前进样口
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16InjPortFront == 1)
                            {
                                value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.FPActualTemp * 10);
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                    case 10: //后进样口
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16InjPortBehind == 1)
                            {
                                value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.BPActualTemp * 10);
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                    case 11: // 柱箱
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16Col == 1)
                            {
                                value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.ColActualTemp * 10);
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                    case 12: //前检测器
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16InjPortFront == 1)
                            {
                                if (CProfileDevice.m_DevParam.syspara.u16DetFrontType == 0)
                                {
                                    value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.fDetActualTemp * 10);
                                }
                                else if (CProfileDevice.m_DevParam.syspara.u16DetFrontType == 1)
                                {
                                    value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.fDetActualTemp * 10);
                                }
                                else
                                {
                                    value = 0;
                                }
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                    case 13: //中检测器
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16DetInter == 1)
                            {
                                if (CProfileDevice.m_DevParam.syspara.u16DetInterType == 0)
                                {
                                    value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.iDetActualTemp * 10);
                                }
                                else if (CProfileDevice.m_DevParam.syspara.u16DetInterType == 1)
                                {
                                    value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.iDetActualTemp * 10);
                                }
                                else
                                {
                                    value = 0;
                                }
                            }
                            else if (CProfileDevice.m_DevParam.syspara.u16AuxHeater1 == 1)
                            {
                                value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.AuxActualTemp1 * 10);
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                    case 14: //后检测器
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16DetBehind == 1)
                            {
                                if (CProfileDevice.m_DevParam.syspara.u16DetBehindType == 0)
                                {
                                    value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.bDetActualTemp * 10);
                                }
                                else if (CProfileDevice.m_DevParam.syspara.u16DetBehindType == 1)
                                {
                                    value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.bDetActualTemp * 10);
                                }
                                else if (CProfileDevice.m_DevParam.syspara.u16AuxHeater2 == 1)
                                {
                                    value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.AuxActualTemp2 * 10);
                                }
                                else
                                {
                                    value = 0;
                                }
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                    case 15: //前点火信号
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16DetFrontType == 1)
                            {
                                value = globaldata.m_dpbuffer.ShowList.showDet.fDetStatue;
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                    case 16: //后点火信号
                        {
                            if (CProfileDevice.m_DevParam.syspara.u16DetInterType == 1)
                            {
                                value = globaldata.m_dpbuffer.ShowList.showDet.fDetStatue;
                            }
                            else
                            {
                                value = 0;
                            }
                        }
                        break;
                }
            }
            return value;
        }

        //static ushort slavereadhreg(ushort address)
        //{
        //    ushort value = 0;
        //    ushort baseaddress = 20;
        //    address = (ushort)(address - 1);
        //    int listnum = SharedSpace.Data.listValue.Count;
        //    int readnum = (address - baseaddress) / 2;

        //    if (readnum <= listnum - 1 && listnum > 0 && address >= 20)
        //    {
        //        // lock(CKVocAnalyzer.GlobalCKV.valueparamlist){

        //        try
        //        {
        //            ushort[] s = new ushort[2];
        //            float[] f = new float[2];
        //            {
        //                f[0] = float.Parse(SharedSpace.Data.listValue[readnum].vale.ToString());
        //                Buffer.BlockCopy(f, 2, s, 0, 2);
        //                Buffer.BlockCopy(f, 0, s, 2, 2);
        //            }
        //            value = s[(address - baseaddress) % 2];
        //        }
        //        catch
        //        {

        //        }
        //        //}
        //    }


        //    if (address >= 2 && address < 20)
        //    {
        //        switch (address)
        //        {
        //            case 2:
        //                {
        //                    value = (ushort)SharedSpace.Data.typesint;
        //                }
        //                break;
        //            case 3:
        //                {
        //                    value = SharedSpace.Data.change == true ? (ushort)1 : (ushort)0;
        //                }
        //                break;
        //            case 4:
        //                {
        //                    value = globaldata.m_hmibuffer.gcinfo.HMIMac[0];
        //                }
        //                break;
        //            case 5:
        //                {
        //                    value = globaldata.m_hmibuffer.gcinfo.HMIMac[1];
        //                }
        //                break;
        //            case 6:
        //                {
        //                    value = globaldata.m_hmibuffer.gcinfo.HMIMac[2];
        //                }
        //                break;
        //            case 7: //设备联机状态
        //                {
        //                    value = (ushort)(globaldata.m_hmibuffer.gcinfo.hmioffline ? 1 : 0);
        //                }
        //                break;
        //            case 8: //HMI状态
        //                {
        //                    value = globaldata.m_hmibuffer.gcinfo.methodstatus;
        //                }
        //                break;
        //            case 9: //前进样口
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16InjPortFront == 1)
        //                    {
        //                        value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.FPActualTemp * 10);
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 10: //后进样口
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16InjPortBehind == 1)
        //                    {
        //                        value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.BPActualTemp * 10);
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 11: // 柱箱
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16Col == 1)
        //                    {
        //                        value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.ColActualTemp * 10);
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 12: //前检测器
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16InjPortFront == 1)
        //                    {
        //                        if (CProfileDevice.m_DevParam.syspara.u16DetFrontType == 0)
        //                        {
        //                            value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.fDetActualTemp * 10);
        //                        }
        //                        else if (CProfileDevice.m_DevParam.syspara.u16DetFrontType == 1)
        //                        {
        //                            value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.fDetActualTemp * 10);
        //                        }
        //                        else
        //                        {
        //                            value = 0;
        //                        }
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 13: //中检测器
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16DetInter == 1)
        //                    {
        //                        if (CProfileDevice.m_DevParam.syspara.u16DetInterType == 0)
        //                        {
        //                            value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.iDetActualTemp * 10);
        //                        }
        //                        else if (CProfileDevice.m_DevParam.syspara.u16DetInterType == 1)
        //                        {
        //                            value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.iDetActualTemp * 10);
        //                        }
        //                        else
        //                        {
        //                            value = 0;
        //                        }
        //                    }
        //                    else if (CProfileDevice.m_DevParam.syspara.u16AuxHeater1 == 1)
        //                    {
        //                        value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.AuxActualTemp1 * 10);
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 14: //后检测器
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16DetBehind == 1)
        //                    {
        //                        if (CProfileDevice.m_DevParam.syspara.u16DetBehindType == 0)
        //                        {
        //                            value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.bDetActualTemp * 10);
        //                        }
        //                        else if (CProfileDevice.m_DevParam.syspara.u16DetBehindType == 1)
        //                        {
        //                            value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.bDetActualTemp * 10);
        //                        }
        //                        else if (CProfileDevice.m_DevParam.syspara.u16AuxHeater2 == 1)
        //                        {
        //                            value = (ushort)(globaldata.m_dpbuffer.ShowList.showtemp.AuxActualTemp2 * 10);
        //                        }
        //                        else
        //                        {
        //                            value = 0;
        //                        }
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 15: //前点火信号
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16DetFrontType == 1)
        //                    {
        //                        value = globaldata.m_dpbuffer.ShowList.showDet.fDetStatue;
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 16: //后点火信号
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16DetInterType == 1)
        //                    {
        //                        value = globaldata.m_dpbuffer.ShowList.showDet.fDetStatue;
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 17: //前检测器值
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16DetFront == 1)
        //                    {
        //                        value = (ushort)(globaldata.m_dpbuffer.ShowList.showDet.fDetValue * 1000);
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 18: //中检测器值
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16DetInter == 1)
        //                    {
        //                        value = (ushort)(globaldata.m_dpbuffer.ShowList.showDet.iDetValue * 1000);
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //            case 19: //后检测器值
        //                {
        //                    if (CProfileDevice.m_DevParam.syspara.u16DetBehind == 1)
        //                    {
        //                        value = (ushort)(globaldata.m_dpbuffer.ShowList.showDet.bDetValue * 1000);
        //                    }
        //                    else
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //                break;
        //        }

        //    }
        //    return value;
        //}

        static void slavewirtehreg(ushort address, ushort value)
        {
           // Console.WriteLine("MoudbusSlave Wirte adder:" + address.ToString() + " value:" + value.ToString());
        }

        SlaveReadCoilsRegister MySlaveReadCoilsRegister;
        SlaveWriteCoilsRegister MySlaveWriteCoilsRegister;
        public void setCoilsRegisterFunc(ushort startaddr, ushort nreg)
        {
            
            MySlaveReadCoilsRegister = new SlaveReadCoilsRegister(slavereadcreg);
            MySlaveWriteCoilsRegister = new SlaveWriteCoilsRegister(slavewirtecreg);
            fnLibModbusSlaveCoilsRegister(hModbusHandle, MySlaveReadCoilsRegister, MySlaveWriteCoilsRegister, startaddr, nreg);
        }

        public static ushort slavereadcreg(ushort address)
        {

            ushort value = 0;
            switch (address)
            {
                case 16:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[0];
                    break;
                case 17:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[1];
                    break;
                case 18:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[2];
                    break;
                case 19:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[3];
                    break;
                case 20:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[4];
                    break;
                case 21:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[5];
                    break;
                case 22:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[6];
                    break;
                case 23:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[7];
                    break;
                case 24:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[8];
                    break;
                case 25:
                    value = globaldata.m_hmibuffer.gcinfo.TenRelay[9];
                    break;
                default:
                    value = 0;
                    break;
            }
         //   Console.WriteLine("MoudbusSlave Read Holding adder is " + CKVocAnalyzer.GlobalCKV.valueparamlist.ToString());
            return value;

         
        }


        public static void slavewirtecreg(ushort address, ushort value)
        {
            //Console.WriteLine("MoudbusSlave Wirte adder:" + address.ToString() + " value:" + value.ToString());
        }





    }
}
