From 5f5d989a5c4834a4f4f6c31c2526e8c1e4b74bbc Mon Sep 17 00:00:00 2001
From: g8bpq <john.wiseman@cantab.net>
Date: Sun, 15 Oct 2023 07:30:59 +0100
Subject: [PATCH] 0.0.0.70

---
 QtSoundModem-DESKTOP-MHE5LO8.vcxproj      |  292 --
 QtSoundModem-HPLaptop.vcxproj             |  288 --
 QtSoundModem.cpp                          |  560 ++-
 QtSoundModem.cpp.bak                      | 2866 -------------
 QtSoundModem.h                            |    8 +-
 QtSoundModem.ui                           |  122 +-
 QtSoundModem.vcxproj-DESKTOP-MHE5LO8.user |   34 -
 QtSoundModem.vcxproj-HPLaptop.user        |   34 -
 QtSoundModem.vcxproj.user                 |   10 +-
 SMMain-DESKTOP-MHE5LO8.c                  | 1433 -------
 SMMain-HPLaptop.c                         | 1381 -------
 SMMain.c                                  |    4 +-
 UZ7HOStuff-DESKTOP-MHE5LO8.h              | 1110 -----
 UZ7HOStuff-HPLaptop.h                     | 1023 -----
 UZ7HOStuff.h                              |    7 +-
 UZ7HOStuff.h.bak                          | 1049 -----
 agwlib.h                                  |   45 -
 ais.h                                     |    8 -
 aprs_tt.h                                 |  191 -
 audio_stats.h                             |    7 -
 ax25_link.h                               |   88 -
 ax25_mod-DESKTOP-MHE5LO8.c                | 1810 ---------
 ax25_pad2.h                               |   55 -
 beacon.h                                  |    6 -
 cdigipeater.h                             |   62 -
 cm108.h                                   |    5 -
 config.h                                  |  262 --
 decode_aprs.h                             |  150 -
 dedupe.h                                  |   10 -
 demod.h                                   |   17 -
 demod_afsk.h                              |    8 -
 demod_psk.h                               |    7 -
 digipeater.h                              |   78 -
 dlq.h                                     |  148 -
 dns_sd_common.h                           |    7 -
 dns_sd_dw.h                               |   10 -
 dtime_now.h                               |   18 -
 dtmf.h                                    |   14 -
 dwgps.h                                   |   61 -
 dwgpsd.h                                  |   22 -
 dwgpsnmea.h                               |   32 -
 dwsock.h                                  |   21 -
 encode_aprs.h                             |   17 -
 fcs_calc.h                                |   11 -
 fsk_filters.h                             |    7 -
 fsk_gen_filter.h                          |   15 -
 gen_tone.h                                |   17 -
 grm_sym.h                                 |  501 ---
 hdlc_send.h                               |   17 -
 igate.h                                   |  128 -
 il2p.c.bak                                | 4502 ---------------------
 kiss.h                                    |   24 -
 kiss_frame.h                              |  126 -
 kissnet.h                                 |   29 -
 kissserial.h                              |   23 -
 latlong.h                                 |   24 -
 log.h                                     |   19 -
 main.cpp                                  |    1 -
 mgn_icon.h                                |  276 --
 mheard.h                                  |   20 -
 morse.h                                   |    8 -
 multi_modem.h                             |   24 -
 pfilter.h                                 |   13 -
 ptt.h                                     |   26 -
 recv.h                                    |    6 -
 redecode.h                                |   15 -
 release/moc_predefs.h                     |   11 +
 rpack.h                                   |   94 -
 rrbb.h                                    |   92 -
 serial_port.h                             |   32 -
 server.h                                  |   32 -
 sm_main.c                                 |    8 +-
 symbols.h                                 |   19 -
 telemetry.h                               |   15 -
 tq.h                                      |   41 -
 tt_text.h                                 |   38 -
 tt_user.h                                 |   15 -
 tune.h                                    |    1 -
 version.h                                 |   21 -
 waypoint.h                                |   24 -
 xid.h                                     |   32 -
 xmit.h                                    |   27 -
 82 files changed, 265 insertions(+), 19449 deletions(-)
 delete mode 100644 QtSoundModem-DESKTOP-MHE5LO8.vcxproj
 delete mode 100644 QtSoundModem-HPLaptop.vcxproj
 delete mode 100644 QtSoundModem.cpp.bak
 delete mode 100644 QtSoundModem.vcxproj-DESKTOP-MHE5LO8.user
 delete mode 100644 QtSoundModem.vcxproj-HPLaptop.user
 delete mode 100644 SMMain-DESKTOP-MHE5LO8.c
 delete mode 100644 SMMain-HPLaptop.c
 delete mode 100644 UZ7HOStuff-DESKTOP-MHE5LO8.h
 delete mode 100644 UZ7HOStuff-HPLaptop.h
 delete mode 100644 UZ7HOStuff.h.bak
 delete mode 100644 agwlib.h
 delete mode 100644 ais.h
 delete mode 100644 aprs_tt.h
 delete mode 100644 audio_stats.h
 delete mode 100644 ax25_link.h
 delete mode 100644 ax25_mod-DESKTOP-MHE5LO8.c
 delete mode 100644 ax25_pad2.h
 delete mode 100644 beacon.h
 delete mode 100644 cdigipeater.h
 delete mode 100644 cm108.h
 delete mode 100644 config.h
 delete mode 100644 decode_aprs.h
 delete mode 100644 dedupe.h
 delete mode 100644 demod.h
 delete mode 100644 demod_afsk.h
 delete mode 100644 demod_psk.h
 delete mode 100644 digipeater.h
 delete mode 100644 dlq.h
 delete mode 100644 dns_sd_common.h
 delete mode 100644 dns_sd_dw.h
 delete mode 100644 dtime_now.h
 delete mode 100644 dtmf.h
 delete mode 100644 dwgps.h
 delete mode 100644 dwgpsd.h
 delete mode 100644 dwgpsnmea.h
 delete mode 100644 dwsock.h
 delete mode 100644 encode_aprs.h
 delete mode 100644 fcs_calc.h
 delete mode 100644 fsk_filters.h
 delete mode 100644 fsk_gen_filter.h
 delete mode 100644 gen_tone.h
 delete mode 100644 grm_sym.h
 delete mode 100644 hdlc_send.h
 delete mode 100644 igate.h
 delete mode 100644 il2p.c.bak
 delete mode 100644 kiss.h
 delete mode 100644 kiss_frame.h
 delete mode 100644 kissnet.h
 delete mode 100644 kissserial.h
 delete mode 100644 latlong.h
 delete mode 100644 log.h
 delete mode 100644 mgn_icon.h
 delete mode 100644 mheard.h
 delete mode 100644 morse.h
 delete mode 100644 multi_modem.h
 delete mode 100644 pfilter.h
 delete mode 100644 ptt.h
 delete mode 100644 recv.h
 delete mode 100644 redecode.h
 create mode 100644 release/moc_predefs.h
 delete mode 100644 rpack.h
 delete mode 100644 rrbb.h
 delete mode 100644 serial_port.h
 delete mode 100644 server.h
 delete mode 100644 symbols.h
 delete mode 100644 telemetry.h
 delete mode 100644 tq.h
 delete mode 100644 tt_text.h
 delete mode 100644 tt_user.h
 delete mode 100644 tune.h
 delete mode 100644 version.h
 delete mode 100644 waypoint.h
 delete mode 100644 xid.h
 delete mode 100644 xmit.h

diff --git a/QtSoundModem-DESKTOP-MHE5LO8.vcxproj b/QtSoundModem-DESKTOP-MHE5LO8.vcxproj
deleted file mode 100644
index adcd4b6..0000000
--- a/QtSoundModem-DESKTOP-MHE5LO8.vcxproj
+++ /dev/null
@@ -1,292 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <ItemGroup Label="ProjectConfigurations">
-    <ProjectConfiguration Include="Release|Win32">
-      <Configuration>Release</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Debug|Win32">
-      <Configuration>Debug</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-  </ItemGroup>
-  <PropertyGroup Label="Globals">
-    <ProjectGuid>{4EDE958E-D0AC-37B4-81F7-78313A262DCD}</ProjectGuid>
-    <RootNamespace>QtSoundModem</RootNamespace>
-    <Keyword>QtVS_v304</Keyword>
-    <WindowsTargetPlatformVersion>10.0.17763.0</WindowsTargetPlatformVersion>
-    <WindowsTargetPlatformMinVersion>10.0.19041.0</WindowsTargetPlatformMinVersion>
-    <QtMsBuild Condition="'$(QtMsBuild)'=='' or !Exists('$(QtMsBuild)\qt.targets')">$(MSBuildProjectDirectory)\QtMsBuild</QtMsBuild>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
-    <PlatformToolset>v141</PlatformToolset>
-    <OutputDirectory>release\</OutputDirectory>
-    <ATLMinimizesCRunTimeLibraryUsage>false</ATLMinimizesCRunTimeLibraryUsage>
-    <CharacterSet>NotSet</CharacterSet>
-    <ConfigurationType>Application</ConfigurationType>
-    <IntermediateDirectory>release\</IntermediateDirectory>
-    <PrimaryOutput>QtSoundModem</PrimaryOutput>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
-    <PlatformToolset>v141</PlatformToolset>
-    <OutputDirectory>debug\</OutputDirectory>
-    <ATLMinimizesCRunTimeLibraryUsage>false</ATLMinimizesCRunTimeLibraryUsage>
-    <CharacterSet>NotSet</CharacterSet>
-    <ConfigurationType>Application</ConfigurationType>
-    <IntermediateDirectory>debug\</IntermediateDirectory>
-    <PrimaryOutput>QtSoundModem</PrimaryOutput>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
-  <Target Name="QtMsBuildNotFound" BeforeTargets="CustomBuild;ClCompile" Condition="!Exists('$(QtMsBuild)\qt.targets') or !Exists('$(QtMsBuild)\qt.props')">
-    <Message Importance="High" Text="QtMsBuild: could not locate qt.targets, qt.props; project may not build correctly." />
-  </Target>
-  <ImportGroup Label="ExtensionSettings" />
-  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" />
-  </ImportGroup>
-  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" />
-  </ImportGroup>
-  <PropertyGroup Label="UserMacros" />
-  <ImportGroup Condition="Exists('$(QtMsBuild)\qt_defaults.props')">
-    <Import Project="$(QtMsBuild)\qt_defaults.props" />
-  </ImportGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <OutDir>$(SolutionDir)$(Platform)\$(Configuration)\</OutDir>
-    <IntDir>$(SolutionDir)Intermed\$(Platform)\$(Configuration)\</IntDir>
-    <TargetName>QtSoundModem</TargetName>
-    <IgnoreImportLibrary>true</IgnoreImportLibrary>
-    <LinkIncremental>true</LinkIncremental>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <OutDir>$(SolutionDir)$(Platform)\$(Configuration)\</OutDir>
-    <IntDir>$(SolutionDir)Intermed\$(Platform)\$(Configuration)\\</IntDir>
-    <TargetName>QtSoundModem</TargetName>
-    <IgnoreImportLibrary>true</IgnoreImportLibrary>
-    <LinkIncremental>false</LinkIncremental>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <QtInstall>5.14</QtInstall>
-    <QtModules>core;network;gui;widgets;serialport</QtModules>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <QtInstall>5.14.2</QtInstall>
-    <QtModules>core;network;gui;widgets;serialport</QtModules>
-  </PropertyGroup>
-  <ImportGroup Condition="Exists('$(QtMsBuild)\qt.props')">
-    <Import Project="$(QtMsBuild)\qt.props" />
-  </ImportGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>rsid;.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;release;/include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <AdditionalOptions>-Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 %(AdditionalOptions)</AdditionalOptions>
-      <AssemblerListingLocation>$(IntDir)</AssemblerListingLocation>
-      <BrowseInformation>false</BrowseInformation>
-      <DebugInformationFormat>None</DebugInformationFormat>
-      <DisableSpecificWarnings>4577;4467;%(DisableSpecificWarnings)</DisableSpecificWarnings>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <Optimization>MaxSpeed</Optimization>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;NDEBUG;QT_NO_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <PreprocessToFile>false</PreprocessToFile>
-      <ProgramDataBaseFileName>$(OutDir)</ProgramDataBaseFileName>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-      <TreatWChar_tAsBuiltInType>true</TreatWChar_tAsBuiltInType>
-      <WarningLevel>Level3</WarningLevel>
-      <MultiProcessorCompilation>true</MultiProcessorCompilation>
-    </ClCompile>
-    <Link>
-      <AdditionalDependencies>libfftw3f-3.lib;shell32.lib;setupapi.lib;WS2_32.Lib;%(AdditionalDependencies)</AdditionalDependencies>
-      <AdditionalLibraryDirectories>C:\opensslx86\lib;C:\Utils\my_sql\mysql-5.7.25-win32\lib;C:\Utils\postgresqlx86\pgsql\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <AdditionalOptions>"/MANIFESTDEPENDENCY:type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' publicKeyToken='6595b64144ccf1df' language='*' processorArchitecture='*'" %(AdditionalOptions)</AdditionalOptions>
-      <DataExecutionPrevention>true</DataExecutionPrevention>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <IgnoreImportLibrary>true</IgnoreImportLibrary>
-      <LinkIncremental>false</LinkIncremental>
-      <OptimizeReferences>true</OptimizeReferences>
-      <OutputFile>$(OutDir)QtSoundModem.exe</OutputFile>
-      <RandomizedBaseAddress>true</RandomizedBaseAddress>
-      <SubSystem>Windows</SubSystem>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-    </Link>
-    <Midl>
-      <DefaultCharType>Unsigned</DefaultCharType>
-      <EnableErrorChecks>None</EnableErrorChecks>
-      <WarningLevel>0</WarningLevel>
-    </Midl>
-    <ResourceCompile>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;NDEBUG;QT_NO_DEBUG;QT_WIDGETS_LIB;QT_GUI_LIB;QT_NETWORK_LIB;QT_SERIALPORT_LIB;QT_CORE_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-    </ResourceCompile>
-    <QtMoc>
-      <CompilerFlavor>msvc</CompilerFlavor>
-      <Include>./$(Configuration)/moc_predefs.h</Include>
-      <ExecutionDescription>Moc'ing %(Identity)...</ExecutionDescription>
-      <DynamicSource>output</DynamicSource>
-      <QtMocDir>$(IntDir)</QtMocDir>
-      <QtMocFileName>moc_%(Filename).cpp</QtMocFileName>
-    </QtMoc>
-    <QtRcc>
-      <InitFuncName>QtSoundModem</InitFuncName>
-      <Compression>default</Compression>
-      <ExecutionDescription>Rcc'ing %(Identity)...</ExecutionDescription>
-      <QtRccDir>$(IntDir)</QtRccDir>
-      <QtRccFileName>qrc_%(Filename).cpp</QtRccFileName>
-    </QtRcc>
-    <QtUic>
-      <ExecutionDescription>Uic'ing %(Identity)...</ExecutionDescription>
-      <QtUicDir>$(IntDir)</QtUicDir>
-      <QtUicFileName>ui_%(Filename).h</QtUicFileName>
-    </QtUic>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;debug;/include;rsid;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <AdditionalOptions>-Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 %(AdditionalOptions)</AdditionalOptions>
-      <AssemblerListingLocation>$(IntDir)</AssemblerListingLocation>
-      <BrowseInformation>false</BrowseInformation>
-      <DebugInformationFormat>EditAndContinue</DebugInformationFormat>
-      <DisableSpecificWarnings>4577;4467;%(DisableSpecificWarnings)</DisableSpecificWarnings>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <Optimization>Disabled</Optimization>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <PreprocessToFile>false</PreprocessToFile>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-      <TreatWChar_tAsBuiltInType>true</TreatWChar_tAsBuiltInType>
-      <WarningLevel>Level3</WarningLevel>
-      <MultiProcessorCompilation>true</MultiProcessorCompilation>
-      <ProgramDataBaseFileName>$(OutDir)</ProgramDataBaseFileName>
-    </ClCompile>
-    <Link>
-      <AdditionalDependencies>libfftw3f-3.lib;shell32.lib;setupapi.lib;WS2_32.Lib;%(AdditionalDependencies)</AdditionalDependencies>
-      <AdditionalLibraryDirectories>C:\opensslx86\lib;C:\Utils\my_sql\mysql-5.7.25-win32\lib;C:\Utils\postgresqlx86\pgsql\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <AdditionalOptions>"/MANIFESTDEPENDENCY:type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' publicKeyToken='6595b64144ccf1df' language='*' processorArchitecture='*'" %(AdditionalOptions)</AdditionalOptions>
-      <DataExecutionPrevention>true</DataExecutionPrevention>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <IgnoreImportLibrary>true</IgnoreImportLibrary>
-      <OutputFile>$(OutDir)\QtSoundModem.exe</OutputFile>
-      <RandomizedBaseAddress>true</RandomizedBaseAddress>
-      <SubSystem>Windows</SubSystem>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-      <ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
-    </Link>
-    <Midl>
-      <DefaultCharType>Unsigned</DefaultCharType>
-      <EnableErrorChecks>None</EnableErrorChecks>
-      <WarningLevel>0</WarningLevel>
-    </Midl>
-    <ResourceCompile>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;QT_WIDGETS_LIB;QT_GUI_LIB;QT_NETWORK_LIB;QT_SERIALPORT_LIB;QT_CORE_LIB;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-    </ResourceCompile>
-    <QtMoc>
-      <CompilerFlavor>msvc</CompilerFlavor>
-      <Include>./$(Configuration)/moc_predefs.h</Include>
-      <ExecutionDescription>Moc'ing %(Identity)...</ExecutionDescription>
-      <DynamicSource>output</DynamicSource>
-      <QtMocDir>$(IntDir)</QtMocDir>
-      <QtMocFileName>moc_%(Filename).cpp</QtMocFileName>
-    </QtMoc>
-    <QtRcc>
-      <InitFuncName>QtSoundModem</InitFuncName>
-      <Compression>default</Compression>
-      <ExecutionDescription>Rcc'ing %(Identity)...</ExecutionDescription>
-      <QtRccDir>$(IntDir)</QtRccDir>
-      <QtRccFileName>qrc_%(Filename).cpp</QtRccFileName>
-    </QtRcc>
-    <QtUic>
-      <ExecutionDescription>Uic'ing %(Identity)...</ExecutionDescription>
-      <QtUicDir>$(IntDir)</QtUicDir>
-      <QtUicFileName>ui_%(Filename).h</QtUicFileName>
-    </QtUic>
-  </ItemDefinitionGroup>
-  <ItemGroup>
-    <ClCompile Include="ARDOPC.c" />
-    <ClCompile Include="BusyDetect.c" />
-    <ClCompile Include="Config.cpp" />
-    <ClCompile Include="dw9600.c" />
-    <ClCompile Include="hid.c" />
-    <ClCompile Include="il2p.c">
-      <CompileAs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">CompileAsC</CompileAs>
-    </ClCompile>
-    <ClCompile Include="Modulate.c" />
-    <ClCompile Include="QtSoundModem.cpp" />
-    <ClCompile Include="rsid.c" />
-    <ClCompile Include="RSUnit.c" />
-    <ClCompile Include="SMMain.c" />
-    <ClCompile Include="ShowFilter.cpp" />
-    <ClCompile Include="SoundInput.c" />
-    <ClCompile Include="UZ7HOUtils.c" />
-    <ClCompile Include="ardopSampleArrays.c" />
-    <ClCompile Include="ax25.c" />
-    <ClCompile Include="ax25_agw.c" />
-    <ClCompile Include="ax25_demod.c" />
-    <ClCompile Include="ax25_fec.c" />
-    <ClCompile Include="ax25_l2.c" />
-    <ClCompile Include="ax25_mod.c" />
-    <ClCompile Include="berlekamp.c" />
-    <ClCompile Include="galois.c" />
-    <ClCompile Include="kiss_mode.c" />
-    <ClCompile Include="main.cpp" />
-    <ClCompile Include="ofdm.c" />
-    <ClCompile Include="pktARDOP.c" />
-    <ClCompile Include="rs.c" />
-    <ClCompile Include="sm_main.c" />
-    <ClCompile Include="tcpCode.cpp" />
-    <ClCompile Include="Waveout.c" />
-  </ItemGroup>
-  <ItemGroup>
-    <QtMoc Include="QtSoundModem.h">
-    </QtMoc>
-    <ClInclude Include="UZ7HOStuff.h" />
-    <QtMoc Include="tcpCode.h">
-    </QtMoc>
-  </ItemGroup>
-  <ItemGroup>
-    <CustomBuild Include="debug\moc_predefs.h.cbt">
-      <FileType>Document</FileType>
-      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
-      <AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(QTDIR)\mkspecs\features\data\dummy.cpp;%(AdditionalInputs)</AdditionalInputs>
-      <Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">cl -Bx"$(QTDIR)\bin\qmake.exe" -nologo -Zc:wchar_t -FS -Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -Zi -MDd -W3 -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 -wd4577 -wd4467 -E $(QTDIR)\mkspecs\features\data\dummy.cpp 2&gt;NUL &gt;debug\moc_predefs.h</Command>
-      <Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Generate moc_predefs.h</Message>
-      <Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">debug\moc_predefs.h;%(Outputs)</Outputs>
-    </CustomBuild>
-    <CustomBuild Include="release\moc_predefs.h.cbt">
-      <FileType>Document</FileType>
-      <AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(QTDIR)\mkspecs\features\data\dummy.cpp;%(AdditionalInputs)</AdditionalInputs>
-      <Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">cl -Bx"$(QTDIR)\bin\qmake.exe" -nologo -Zc:wchar_t -FS -Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -O2 -MD -W3 -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 -wd4577 -wd4467 -E $(QTDIR)\mkspecs\features\data\dummy.cpp 2&gt;NUL &gt;release\moc_predefs.h</Command>
-      <Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Generate moc_predefs.h</Message>
-      <Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">release\moc_predefs.h;%(Outputs)</Outputs>
-      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
-    </CustomBuild>
-  </ItemGroup>
-  <ItemGroup>
-    <QtUic Include="ModemDialog.ui">
-    </QtUic>
-    <QtUic Include="QtSoundModem.ui">
-    </QtUic>
-    <QtUic Include="calibrateDialog.ui">
-    </QtUic>
-    <QtUic Include="devicesDialog.ui">
-    </QtUic>
-    <QtUic Include="filterWindow.ui">
-    </QtUic>
-  </ItemGroup>
-  <ItemGroup>
-    <QtRcc Include="QtSoundModem.qrc">
-    </QtRcc>
-  </ItemGroup>
-  <ItemGroup>
-    <ResourceCompile Include=".\QtSoundModem_resource.rc" />
-  </ItemGroup>
-  <ItemGroup>
-    <Image Include="QtSoundModem.ico" />
-  </ItemGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
-  <ImportGroup Condition="Exists('$(QtMsBuild)\qt.targets')">
-    <Import Project="$(QtMsBuild)\qt.targets" />
-  </ImportGroup>
-  <ImportGroup Label="ExtensionTargets" />
-</Project>
\ No newline at end of file
diff --git a/QtSoundModem-HPLaptop.vcxproj b/QtSoundModem-HPLaptop.vcxproj
deleted file mode 100644
index 3b99dd0..0000000
--- a/QtSoundModem-HPLaptop.vcxproj
+++ /dev/null
@@ -1,288 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <ItemGroup Label="ProjectConfigurations">
-    <ProjectConfiguration Include="Release|Win32">
-      <Configuration>Release</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Debug|Win32">
-      <Configuration>Debug</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-  </ItemGroup>
-  <PropertyGroup Label="Globals">
-    <ProjectGuid>{4EDE958E-D0AC-37B4-81F7-78313A262DCD}</ProjectGuid>
-    <RootNamespace>QtSoundModem</RootNamespace>
-    <Keyword>QtVS_v304</Keyword>
-    <WindowsTargetPlatformVersion>10.0.19041.0</WindowsTargetPlatformVersion>
-    <WindowsTargetPlatformMinVersion>10.0.19041.0</WindowsTargetPlatformMinVersion>
-    <QtMsBuild Condition="'$(QtMsBuild)'=='' or !Exists('$(QtMsBuild)\qt.targets')">$(MSBuildProjectDirectory)\QtMsBuild</QtMsBuild>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
-    <PlatformToolset>v141</PlatformToolset>
-    <OutputDirectory>release\</OutputDirectory>
-    <ATLMinimizesCRunTimeLibraryUsage>false</ATLMinimizesCRunTimeLibraryUsage>
-    <CharacterSet>NotSet</CharacterSet>
-    <ConfigurationType>Application</ConfigurationType>
-    <IntermediateDirectory>release\</IntermediateDirectory>
-    <PrimaryOutput>QtSoundModem</PrimaryOutput>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
-    <PlatformToolset>v141</PlatformToolset>
-    <OutputDirectory>debug\</OutputDirectory>
-    <ATLMinimizesCRunTimeLibraryUsage>false</ATLMinimizesCRunTimeLibraryUsage>
-    <CharacterSet>NotSet</CharacterSet>
-    <ConfigurationType>Application</ConfigurationType>
-    <IntermediateDirectory>debug\</IntermediateDirectory>
-    <PrimaryOutput>QtSoundModem</PrimaryOutput>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
-  <Target Name="QtMsBuildNotFound" BeforeTargets="CustomBuild;ClCompile" Condition="!Exists('$(QtMsBuild)\qt.targets') or !Exists('$(QtMsBuild)\qt.props')">
-    <Message Importance="High" Text="QtMsBuild: could not locate qt.targets, qt.props; project may not build correctly." />
-  </Target>
-  <ImportGroup Label="ExtensionSettings" />
-  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" />
-  </ImportGroup>
-  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" />
-  </ImportGroup>
-  <PropertyGroup Label="UserMacros" />
-  <ImportGroup Condition="Exists('$(QtMsBuild)\qt_defaults.props')">
-    <Import Project="$(QtMsBuild)\qt_defaults.props" />
-  </ImportGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <OutDir>C:\Dev\Msdev2005\projects\QT\QtSoundModem\Win32\Debug\</OutDir>
-    <IntDir>C:\Dev\Msdev2005\projects\QT\QtSoundModem\Intermed\Win32\Debug\</IntDir>
-    <TargetName>QtSoundModem</TargetName>
-    <IgnoreImportLibrary>true</IgnoreImportLibrary>
-    <LinkIncremental>true</LinkIncremental>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <OutDir>C:\Dev\Msdev2005\projects\QT\QtSoundModem\Win32\Release\</OutDir>
-    <IntDir>C:\Dev\Msdev2005\projects\QT\QtSoundModem\Intermed\Win32\Release\</IntDir>
-    <TargetName>QtSoundModem</TargetName>
-    <IgnoreImportLibrary>true</IgnoreImportLibrary>
-    <LinkIncremental>false</LinkIncremental>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <QtInstall>5.14.2_msvc2017</QtInstall>
-    <QtModules>core;network;gui;widgets;serialport</QtModules>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <QtInstall>5.14.2_msvc2017</QtInstall>
-    <QtModules>core;network;gui;widgets;serialport</QtModules>
-  </PropertyGroup>
-  <ImportGroup Condition="Exists('$(QtMsBuild)\qt.props')">
-    <Import Project="$(QtMsBuild)\qt.props" />
-  </ImportGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>rsid;.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;release;/include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <AdditionalOptions>-Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 %(AdditionalOptions)</AdditionalOptions>
-      <AssemblerListingLocation>$(IntDir)</AssemblerListingLocation>
-      <BrowseInformation>false</BrowseInformation>
-      <DebugInformationFormat>None</DebugInformationFormat>
-      <DisableSpecificWarnings>4577;4467;%(DisableSpecificWarnings)</DisableSpecificWarnings>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <Optimization>MaxSpeed</Optimization>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;NDEBUG;QT_NO_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <PreprocessToFile>false</PreprocessToFile>
-      <ProgramDataBaseFileName>$(OutDir)</ProgramDataBaseFileName>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-      <TreatWChar_tAsBuiltInType>true</TreatWChar_tAsBuiltInType>
-      <WarningLevel>Level3</WarningLevel>
-      <MultiProcessorCompilation>true</MultiProcessorCompilation>
-    </ClCompile>
-    <Link>
-      <AdditionalDependencies>libfftw3f-3.lib;shell32.lib;setupapi.lib;WS2_32.Lib;%(AdditionalDependencies)</AdditionalDependencies>
-      <AdditionalLibraryDirectories>C:\opensslx86\lib;C:\Utils\my_sql\mysql-5.7.25-win32\lib;C:\Utils\postgresqlx86\pgsql\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <AdditionalOptions>"/MANIFESTDEPENDENCY:type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' publicKeyToken='6595b64144ccf1df' language='*' processorArchitecture='*'" %(AdditionalOptions)</AdditionalOptions>
-      <DataExecutionPrevention>true</DataExecutionPrevention>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <IgnoreImportLibrary>true</IgnoreImportLibrary>
-      <LinkIncremental>false</LinkIncremental>
-      <OptimizeReferences>true</OptimizeReferences>
-      <OutputFile>$(OutDir)\QtSoundModem.exe</OutputFile>
-      <RandomizedBaseAddress>true</RandomizedBaseAddress>
-      <SubSystem>Windows</SubSystem>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-    </Link>
-    <Midl>
-      <DefaultCharType>Unsigned</DefaultCharType>
-      <EnableErrorChecks>None</EnableErrorChecks>
-      <WarningLevel>0</WarningLevel>
-    </Midl>
-    <ResourceCompile>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;NDEBUG;QT_NO_DEBUG;QT_WIDGETS_LIB;QT_GUI_LIB;QT_NETWORK_LIB;QT_SERIALPORT_LIB;QT_CORE_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-    </ResourceCompile>
-    <QtMoc>
-      <CompilerFlavor>msvc</CompilerFlavor>
-      <Include>./$(Configuration)/moc_predefs.h</Include>
-      <ExecutionDescription>Moc'ing %(Identity)...</ExecutionDescription>
-      <DynamicSource>output</DynamicSource>
-      <QtMocDir>$(IntDir)</QtMocDir>
-      <QtMocFileName>moc_%(Filename).cpp</QtMocFileName>
-    </QtMoc>
-    <QtRcc>
-      <InitFuncName>QtSoundModem</InitFuncName>
-      <Compression>default</Compression>
-      <ExecutionDescription>Rcc'ing %(Identity)...</ExecutionDescription>
-      <QtRccDir>$(IntDir)</QtRccDir>
-      <QtRccFileName>qrc_%(Filename).cpp</QtRccFileName>
-    </QtRcc>
-    <QtUic>
-      <ExecutionDescription>Uic'ing %(Identity)...</ExecutionDescription>
-      <QtUicDir>$(IntDir)</QtUicDir>
-      <QtUicFileName>ui_%(Filename).h</QtUicFileName>
-    </QtUic>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;debug;/include;rsid;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <AdditionalOptions>-Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 %(AdditionalOptions)</AdditionalOptions>
-      <AssemblerListingLocation>$(IntDir)</AssemblerListingLocation>
-      <BrowseInformation>false</BrowseInformation>
-      <DebugInformationFormat>EditAndContinue</DebugInformationFormat>
-      <DisableSpecificWarnings>4577;4467;%(DisableSpecificWarnings)</DisableSpecificWarnings>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <Optimization>Disabled</Optimization>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <PreprocessToFile>false</PreprocessToFile>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-      <TreatWChar_tAsBuiltInType>true</TreatWChar_tAsBuiltInType>
-      <WarningLevel>Level3</WarningLevel>
-      <MultiProcessorCompilation>true</MultiProcessorCompilation>
-      <ProgramDataBaseFileName>$(OutDir)</ProgramDataBaseFileName>
-    </ClCompile>
-    <Link>
-      <AdditionalDependencies>libfftw3f-3.lib;shell32.lib;setupapi.lib;WS2_32.Lib;%(AdditionalDependencies)</AdditionalDependencies>
-      <AdditionalLibraryDirectories>C:\opensslx86\lib;C:\Utils\my_sql\mysql-5.7.25-win32\lib;C:\Utils\postgresqlx86\pgsql\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <AdditionalOptions>"/MANIFESTDEPENDENCY:type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' publicKeyToken='6595b64144ccf1df' language='*' processorArchitecture='*'" %(AdditionalOptions)</AdditionalOptions>
-      <DataExecutionPrevention>true</DataExecutionPrevention>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <IgnoreImportLibrary>true</IgnoreImportLibrary>
-      <OutputFile>$(OutDir)\QtSoundModem.exe</OutputFile>
-      <RandomizedBaseAddress>true</RandomizedBaseAddress>
-      <SubSystem>Windows</SubSystem>
-      <SuppressStartupBanner>true</SuppressStartupBanner>
-      <ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
-    </Link>
-    <Midl>
-      <DefaultCharType>Unsigned</DefaultCharType>
-      <EnableErrorChecks>None</EnableErrorChecks>
-      <WarningLevel>0</WarningLevel>
-    </Midl>
-    <ResourceCompile>
-      <PreprocessorDefinitions>_WINDOWS;UNICODE;_UNICODE;WIN32;_ENABLE_EXTENDED_ALIGNED_STORAGE;QT_WIDGETS_LIB;QT_GUI_LIB;QT_NETWORK_LIB;QT_SERIALPORT_LIB;QT_CORE_LIB;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
-    </ResourceCompile>
-    <QtMoc>
-      <CompilerFlavor>msvc</CompilerFlavor>
-      <Include>./$(Configuration)/moc_predefs.h</Include>
-      <ExecutionDescription>Moc'ing %(Identity)...</ExecutionDescription>
-      <DynamicSource>output</DynamicSource>
-      <QtMocDir>$(IntDir)</QtMocDir>
-      <QtMocFileName>moc_%(Filename).cpp</QtMocFileName>
-    </QtMoc>
-    <QtRcc>
-      <InitFuncName>QtSoundModem</InitFuncName>
-      <Compression>default</Compression>
-      <ExecutionDescription>Rcc'ing %(Identity)...</ExecutionDescription>
-      <QtRccDir>$(IntDir)</QtRccDir>
-      <QtRccFileName>qrc_%(Filename).cpp</QtRccFileName>
-    </QtRcc>
-    <QtUic>
-      <ExecutionDescription>Uic'ing %(Identity)...</ExecutionDescription>
-      <QtUicDir>$(IntDir)</QtUicDir>
-      <QtUicFileName>ui_%(Filename).h</QtUicFileName>
-    </QtUic>
-  </ItemDefinitionGroup>
-  <ItemGroup>
-    <ClCompile Include="ARDOPC.c" />
-    <ClCompile Include="BusyDetect.c" />
-    <ClCompile Include="Config.cpp" />
-    <ClCompile Include="hid.c" />
-    <ClCompile Include="Modulate.c" />
-    <ClCompile Include="QtSoundModem.cpp" />
-    <ClCompile Include="rsid.c" />
-    <ClCompile Include="RSUnit.c" />
-    <ClCompile Include="SMMain.c" />
-    <ClCompile Include="ShowFilter.cpp" />
-    <ClCompile Include="SoundInput.c" />
-    <ClCompile Include="UZ7HOUtils.c" />
-    <ClCompile Include="ardopSampleArrays.c" />
-    <ClCompile Include="ax25.c" />
-    <ClCompile Include="ax25_agw.c" />
-    <ClCompile Include="ax25_demod.c" />
-    <ClCompile Include="ax25_fec.c" />
-    <ClCompile Include="ax25_l2.c" />
-    <ClCompile Include="ax25_mod.c" />
-    <ClCompile Include="berlekamp.c" />
-    <ClCompile Include="galois.c" />
-    <ClCompile Include="kiss_mode.c" />
-    <ClCompile Include="main.cpp" />
-    <ClCompile Include="ofdm.c" />
-    <ClCompile Include="pktARDOP.c" />
-    <ClCompile Include="rs.c" />
-    <ClCompile Include="sm_main.c" />
-    <ClCompile Include="tcpCode.cpp" />
-    <ClCompile Include="Waveout.c" />
-  </ItemGroup>
-  <ItemGroup>
-    <QtMoc Include="QtSoundModem.h">
-    </QtMoc>
-    <ClInclude Include="UZ7HOStuff.h" />
-    <QtMoc Include="tcpCode.h">
-    </QtMoc>
-  </ItemGroup>
-  <ItemGroup>
-    <CustomBuild Include="debug\moc_predefs.h.cbt">
-      <FileType>Document</FileType>
-      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
-      <AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(QTDIR)\mkspecs\features\data\dummy.cpp;%(AdditionalInputs)</AdditionalInputs>
-      <Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">cl -Bx"$(QTDIR)\bin\qmake.exe" -nologo -Zc:wchar_t -FS -Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -Zi -MDd -W3 -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 -wd4577 -wd4467 -E $(QTDIR)\mkspecs\features\data\dummy.cpp 2&gt;NUL &gt;debug\moc_predefs.h</Command>
-      <Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Generate moc_predefs.h</Message>
-      <Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">debug\moc_predefs.h;%(Outputs)</Outputs>
-    </CustomBuild>
-    <CustomBuild Include="release\moc_predefs.h.cbt">
-      <FileType>Document</FileType>
-      <AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(QTDIR)\mkspecs\features\data\dummy.cpp;%(AdditionalInputs)</AdditionalInputs>
-      <Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">cl -Bx"$(QTDIR)\bin\qmake.exe" -nologo -Zc:wchar_t -FS -Zc:rvalueCast -Zc:inline -Zc:strictStrings -Zc:throwingNew -Zc:referenceBinding -Zc:__cplusplus -O2 -MD -W3 -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 -wd4577 -wd4467 -E $(QTDIR)\mkspecs\features\data\dummy.cpp 2&gt;NUL &gt;release\moc_predefs.h</Command>
-      <Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Generate moc_predefs.h</Message>
-      <Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">release\moc_predefs.h;%(Outputs)</Outputs>
-      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
-    </CustomBuild>
-  </ItemGroup>
-  <ItemGroup>
-    <QtUic Include="ModemDialog.ui">
-    </QtUic>
-    <QtUic Include="QtSoundModem.ui">
-    </QtUic>
-    <QtUic Include="calibrateDialog.ui">
-    </QtUic>
-    <QtUic Include="devicesDialog.ui">
-    </QtUic>
-    <QtUic Include="filterWindow.ui">
-    </QtUic>
-  </ItemGroup>
-  <ItemGroup>
-    <QtRcc Include="QtSoundModem.qrc">
-    </QtRcc>
-  </ItemGroup>
-  <ItemGroup>
-    <ResourceCompile Include=".\QtSoundModem_resource.rc" />
-  </ItemGroup>
-  <ItemGroup>
-    <Image Include="QtSoundModem.ico" />
-  </ItemGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
-  <ImportGroup Condition="Exists('$(QtMsBuild)\qt.targets')">
-    <Import Project="$(QtMsBuild)\qt.targets" />
-  </ImportGroup>
-  <ImportGroup Label="ExtensionTargets" />
-</Project>
\ No newline at end of file
diff --git a/QtSoundModem.cpp b/QtSoundModem.cpp
index f83e8b7..9c0eb7b 100644
--- a/QtSoundModem.cpp
+++ b/QtSoundModem.cpp
@@ -51,8 +51,7 @@ along with QtSoundModem.  If not, see http://www.gnu.org/licenses
 
 
 QImage *Constellation[4];
-QImage *Waterfall[4] = { 0,0,0,0 };
-QImage *Header[4];
+QImage *Waterfall = 0;
 QLabel *DCDLabel[4];
 QLineEdit *chanOffsetLabel[4];
 QImage *DCDLed[4];
@@ -60,8 +59,8 @@ QImage *DCDLed[4];
 QImage *RXLevel;
 QImage *RXLevel2;
 
-QLabel *WaterfallCopy[2];
-QLabel *HeaderCopy[2];
+QLabel *WaterfallCopy;
+
 QLabel * RXLevelCopy;
 QLabel * RXLevel2Copy;
 
@@ -75,6 +74,8 @@ QList<QSerialPortInfo> Ports = QSerialPortInfo::availablePorts();
 
 void saveSettings();
 void getSettings();
+void DrawModemFreqRange();
+
 extern "C" void CloseSound();
 extern "C" void GetSoundDevices();
 extern "C" char modes_name[modes_count][21];
@@ -122,11 +123,10 @@ extern "C"
 	int Freq_Change(int Chan, int Freq);
 	void set_speed(int snd_ch, int Modem);
 	void init_speed(int snd_ch);
-	void wf_pointer(int snd_ch);
 	void FourierTransform(int NumSamples, short * RealIn, float * RealOut, float * ImagOut, int InverseTransform);
 	void dofft(short * in, float * outr, float * outi);
 	void init_raduga();
-	void wf_Scale(int Chan);
+	void DrawFreqTicks();
 	void AGW_Report_Modem_Change(int port);
 	char * strlop(char * buf, char delim);
 	void sendRSID(int Chan, int dropTX);
@@ -161,6 +161,7 @@ int WaterfallMax = 6000;
 int Configuring = 0;
 bool lockWaterfall = false;
 
+extern "C" int NeedWaterfallHeaders;
 extern "C" float BinSize;
 
 extern "C" { int RSID_SABM[4]; }
@@ -207,7 +208,7 @@ QRgb vbColours[16] = { qRgb(255, 255, 255), qRgb(255, 99, 71), qRgb(255, 215, 0)
 						qRgb(218, 165, 32), qRgb(255, 0, 255) };
 
 unsigned char  WaterfallLines[2][80][4096] = { 0 };
-int NextWaterfallLine[2] = { 0 };
+int NextWaterfallLine[2] = {0, 0};
 
 unsigned int LastLevel = 255;
 unsigned int LastBusy = 255;
@@ -320,8 +321,7 @@ void QtSoundModem::resizeEvent(QResizeEvent* event)
 	QRect r2 = ui.centralWidget->geometry();
 
 	int modemBoxHeight = 34;
-	int waterfallHeight = 118;
-
+	
 	int Width = r.width();
 	int Height = r.height() - 25;
 
@@ -330,7 +330,7 @@ void QtSoundModem::resizeEvent(QResizeEvent* event)
 	int sessionTop;
 	int sessionHeight = 0;
 	int waterfallsTop;
-	int waterfallsHeight = 0;
+	int waterfallsHeight = WaterfallImageHeight;
 
 	ui.modeB->setVisible(soundChannel[1]);
 	ui.centerB->setVisible(soundChannel[1]);
@@ -353,54 +353,14 @@ void QtSoundModem::resizeEvent(QResizeEvent* event)
 	if (soundChannel[2] || soundChannel[3])
 		modemBoxHeight = 60;
 
-	ui.WaterfallA->setVisible(0);
-	ui.HeaderA->setVisible(0);
-	ui.WaterfallB->setVisible(0);
-	ui.HeaderB->setVisible(0);
+	ui.Waterfall->setVisible(0);
 
 	monitorTop = modemBoxHeight + 1;
 
-	if (UsingBothChannels)
-	{
-		// Two waterfalls
+	// Now have one waterfall label containing headers and waterfalls
 
-		// Could have 2 but only want to display 2nd
-
-		if (Firstwaterfall)
-		{
-			ui.WaterfallA->setVisible(1);
-			ui.HeaderA->setVisible(1);
-			waterfallsHeight += waterfallHeight;
-		}
-		if (Secondwaterfall)
-		{
-			ui.WaterfallB->setVisible(1);
-			ui.HeaderB->setVisible(1);
-			waterfallsHeight += waterfallHeight;
-		}
-	}
-	else
-	{
-		// Only one channel so can only be one waterfall
-
-		// Could be Left or Right
-
-		if (Firstwaterfall)
-		{
-			waterfallsHeight += waterfallHeight;
-
-			if (soundChannel[0] == RIGHT)
-			{
-				ui.WaterfallB->setVisible(1);
-				ui.HeaderB->setVisible(1);
-			}
-			else
-			{
-				ui.WaterfallA->setVisible(1);
-				ui.HeaderA->setVisible(1);
-			}
-		}
-	}
+		if (Firstwaterfall || Secondwaterfall)
+			ui.Waterfall->setVisible(1);
 
 	if (AGWServ)
 	{
@@ -412,6 +372,16 @@ void QtSoundModem::resizeEvent(QResizeEvent* event)
 		sessionTable->setVisible(false);
 	}
 
+	// if only displaying one Waterfall, change height of waterfall area
+
+	if (UsingBothChannels == 0  || (Firstwaterfall == 0) || (Secondwaterfall == 0))
+	{
+		waterfallsHeight /= 2;
+	}
+
+	if ((Firstwaterfall == 0) && (Secondwaterfall == 0))
+		waterfallsHeight = 0;
+
 	monitorHeight = Height - sessionHeight - waterfallsHeight - modemBoxHeight;
 	waterfallsTop = Height - waterfallsHeight;
 	sessionTop = Height - (sessionHeight + waterfallsHeight);
@@ -421,28 +391,8 @@ void QtSoundModem::resizeEvent(QResizeEvent* event)
 	if (AGWServ)
 		sessionTable->setGeometry(QRect(0, sessionTop, Width, sessionHeight));
 
-	if (UsingBothChannels && Firstwaterfall && Secondwaterfall)
-	{
-		ui.HeaderA->setGeometry(QRect(0, waterfallsTop, Width, 38));
-		ui.WaterfallA->setGeometry(QRect(0, waterfallsTop + 38, Width, 80));
-		ui.HeaderB->setGeometry(QRect(0, waterfallsTop + waterfallHeight, Width, 38));
-		ui.WaterfallB->setGeometry(QRect(0, waterfallsTop + waterfallHeight + 38, Width, 80));
-		return;
-	}
-
-	// We are only displaying one channel. Normaly will be Waterfall A unless UsingBothChannels but only displaying Right
-
-	if (UsingBothChannels && Firstwaterfall == 0)			// Only Right
-	{
-		ui.HeaderB->setGeometry(QRect(0, waterfallsTop, Width, 38));
-		ui.WaterfallB->setGeometry(QRect(0, waterfallsTop + 38, Width, 80));
-	}
-	else
-	{
-		ui.HeaderA->setGeometry(QRect(0, waterfallsTop, Width, 38));
-		ui.WaterfallA->setGeometry(QRect(0, waterfallsTop + 38, Width, 80));
-	}
-
+	if (waterfallsHeight)
+		ui.Waterfall->setGeometry(QRect(0, waterfallsTop, Width, waterfallsHeight + 2));
 }
 
 QAction * setupMenuLine(QMenu * Menu, char * Label, QObject * parent, int State)
@@ -466,50 +416,40 @@ void QtSoundModem::menuChecked()
 	int state = Act->isChecked();
 
 	if (Act == actWaterfall1)
-	{
-		int oldstate = Firstwaterfall;
 		Firstwaterfall = state;
 
-		if (state != oldstate)
-			initWaterfall(0, state);
-
-	}
 	else if (Act == actWaterfall2)
-	{
-		int oldstate = Secondwaterfall;
 		Secondwaterfall = state;
 
-		if (state != oldstate)
-			initWaterfall(1, state);
+	initWaterfall(Firstwaterfall | Secondwaterfall);
 
-	}
 	saveSettings();
 }
 
-void QtSoundModem::initWaterfall(int chan, int state)
+void QtSoundModem::initWaterfall(int state)
 {
 	if (state == 1)
 	{
-		if (chan == 0)
-		{
-			ui.WaterfallA = new QLabel(ui.centralWidget);
-			WaterfallCopy[0] = ui.WaterfallA;
-		}
-		else
-		{
-			ui.WaterfallB = new QLabel(ui.centralWidget);
-			WaterfallCopy[1] = ui.WaterfallB;
-		}
-		Waterfall[chan] = new QImage(1024, 80, QImage::Format_RGB32);
-		Waterfall[chan]->fill(black);
+	//	if (ui.Waterfall)
+	//	{
+	//		delete ui.Waterfall;
+	//		ui.Waterfall = new QLabel(ui.centralWidget);
+	//	}
+		WaterfallCopy = ui.Waterfall;
+
+		Waterfall = new QImage(1024, WaterfallImageHeight + 2, QImage::Format_RGB32);
+
+		NeedWaterfallHeaders = 1;
+
 	}
 	else
 	{
-		delete(Waterfall[chan]);
-		Waterfall[chan] = 0;
+		delete(Waterfall);
+		Waterfall = 0;
 	}
 
 	QSize Size(800, 602);						// Not actually used, but Event constructor needs it
+
 	QResizeEvent *event = new QResizeEvent(Size, Size);
 	QApplication::sendEvent(this, event);
 }
@@ -714,8 +654,6 @@ QtSoundModem::QtSoundModem(QWidget *parent) : QMainWindow(parent)
 	actAbout = ui.menuBar->addAction("&About");
 	connect(actAbout, SIGNAL(triggered()), this, SLOT(doAbout()));
 
-	Header[0] = new QImage(1024, 38, QImage::Format_RGB32);
-	Header[1] = new QImage(1024, 38, QImage::Format_RGB32);
 	RXLevel = new QImage(150, 10, QImage::Format_RGB32);
 	RXLevel->fill(white);
 	ui.RXLevel->setPixmap(QPixmap::fromImage(*RXLevel));
@@ -761,41 +699,16 @@ QtSoundModem::QtSoundModem(QWidget *parent) : QMainWindow(parent)
 	chanOffsetLabel[2] = ui.RXOffsetC;
 	chanOffsetLabel[3] = ui.RXOffsetD;
 
-	//	Waterfall[0]->setColorCount(16);
-	//	Waterfall[1]->setColorCount(16);
+	WaterfallCopy = ui.Waterfall;
 
+	initWaterfall(Firstwaterfall | Secondwaterfall);
 
-	//	for (i = 0; i < 16; i++)
-	//	{
-	//	Waterfall[0]->setColor(i, vbColours[i]);
-	//		Waterfall[1]->setColor(i, vbColours[i]);
-	//	}
-
-	WaterfallCopy[0] = ui.WaterfallA;
-	WaterfallCopy[1] = ui.WaterfallB;
-
-	initWaterfall(0, 1);
-	initWaterfall(1, 1);
-
-	Header[0]->fill(black);
-	Header[1]->fill(black);
-
-	HeaderCopy[0] = ui.HeaderA;
-	HeaderCopy[1] = ui.HeaderB;
 	monWindowCopy = ui.monWindow;
 
 	ui.monWindow->document()->setMaximumBlockCount(10000);
 
 //	connect(ui.monWindow, SIGNAL(selectionChanged()), this, SLOT(onTEselectionChanged()));
 
-	ui.HeaderA->setPixmap(QPixmap::fromImage(*Header[0]));
-	ui.HeaderB->setPixmap(QPixmap::fromImage(*Header[1]));
-
-	wf_pointer(soundChannel[0]);
-	wf_pointer(soundChannel[1]);
-	wf_Scale(0);
-	wf_Scale(1);
-
 	connect(ui.modeA, SIGNAL(currentIndexChanged(int)), this, SLOT(clickedSlotI(int)));
 	connect(ui.modeB, SIGNAL(currentIndexChanged(int)), this, SLOT(clickedSlotI(int)));
 	connect(ui.modeC, SIGNAL(currentIndexChanged(int)), this, SLOT(clickedSlotI(int)));
@@ -825,7 +738,6 @@ QtSoundModem::QtSoundModem(QWidget *parent) : QMainWindow(parent)
 
 	ui.DCDSlider->setValue(dcd_threshold);
 
-
 	char valChar[32];
 	sprintf(valChar, "RX Offset %d", rxOffset);
 	ui.RXOffsetLabel->setText(valChar);
@@ -925,7 +837,7 @@ void extSetOffset(int chan)
 	sprintf(valChar, "%d", chanOffset[chan]);
 	chanOffsetLabel[chan]->setText(valChar);
 
-	wf_pointer(soundChannel[chan]);
+	NeedWaterfallHeaders = true;
 
 	pnt_change[0] = 1;
 	pnt_change[1] = 1;
@@ -968,6 +880,15 @@ void QtSoundModem::MyTimerSlot()
 		DoPSKWindows();
 	}
 
+	if (NeedWaterfallHeaders)
+	{
+		NeedWaterfallHeaders = 0;
+
+		Waterfall->fill(black);
+		DrawModemFreqRange();
+		DrawFreqTicks();
+	}
+
 	show_grid();
 }
 
@@ -1141,8 +1062,7 @@ void QtSoundModem::clickedSlotI(int i)
 		sprintf(valChar, "RX Offset %d",rxOffset);
 		ui.RXOffsetLabel->setText(valChar);
 
-		wf_pointer(soundChannel[0]);
-		wf_pointer(soundChannel[1]);
+		NeedWaterfallHeaders = true;
 
 		pnt_change[0] = 1;
 		pnt_change[1] = 1;
@@ -2432,8 +2352,7 @@ void QtSoundModem::deviceaccept()
 	ClosePTTPort();
 	OpenPTTPort();
 
-	wf_pointer(soundChannel[0]);
-	wf_pointer(soundChannel[1]);
+	NeedWaterfallHeaders = true;
 
 	delete(Dev);
 	saveSettings();
@@ -2484,16 +2403,10 @@ void QtSoundModem::doRestartWF()
 {
 	lockWaterfall = true;
 
-	if (Firstwaterfall)
+	if (Firstwaterfall | Secondwaterfall)
 	{
-		initWaterfall(0, 0);
-		initWaterfall(0, 1);
-	}
-
-	if (Secondwaterfall)
-	{
-		initWaterfall(1, 0);
-		initWaterfall(1, 1);
+		initWaterfall(0);
+		initWaterfall(1);
 	}
 
 	delete(RXLevel);
@@ -2581,7 +2494,7 @@ void QtSoundModem::RefreshSpectrum(unsigned char * Data)
 
 	// Last 4 bytes are level busy and Tuning lines
 
-	Waterfall[0]->fill(Black);
+	Waterfall->fill(Black);
 
 	if (Data[206] != LastLevel)
 	{
@@ -2602,13 +2515,13 @@ void QtSoundModem::RefreshSpectrum(unsigned char * Data)
 		if (val > 63)
 			val = 63;
 
-		Waterfall[0]->setPixel(i, val, Yellow);
+		Waterfall->setPixel(i, val, Yellow);
 		if (val < 62)
-			Waterfall[0]->setPixel(i, val + 1, Gold);
+			Waterfall->setPixel(i, val + 1, Gold);
 		Data++;
 	}
 
-	ui.WaterfallA->setPixmap(QPixmap::fromImage(*Waterfall[0]));
+	ui.Waterfall->setPixmap(QPixmap::fromImage(*Waterfall));
 
 }
 
@@ -2644,7 +2557,7 @@ void QtSoundModem::RefreshWaterfall(int snd_ch, unsigned char * Data)
 {
 	int j;
 	unsigned char * Line;
-	int len = Waterfall[0]->bytesPerLine();
+	int len = Waterfall->bytesPerLine();
 	int TopLine = NextWaterfallLine[snd_ch];
 
 	// Write line to cyclic buffer then draw starting with the line just written
@@ -2657,13 +2570,13 @@ void QtSoundModem::RefreshWaterfall(int snd_ch, unsigned char * Data)
 
 	for (j = 63; j > 0; j--)
 	{
-		Line = Waterfall[0]->scanLine(j);
+		Line = Waterfall->scanLine(j);
 		memcpy(Line, &WaterfallLines[snd_ch][TopLine++][0], len);
 		if (TopLine > 63)
 			TopLine = 0;
 	}
 
-	ui.WaterfallA->setPixmap(QPixmap::fromImage(*Waterfall[0]));
+	ui.Waterfall->setPixmap(QPixmap::fromImage(*Waterfall));
 }
 
 void QtSoundModem::sendtoTrace(char * Msg, int tx)
@@ -2742,180 +2655,157 @@ extern "C" int nonGUIMode;
 
 // This draws the Frequency Scale on Waterfall
 
-extern "C" void wf_Scale(int Chan)
+extern "C" void DrawFreqTicks()
 {
 	if (nonGUIMode)
 		return;
 
+	// Draw Frequency Markers on waterfall header(s);
+
 	int x, i;
 	char Textxx[20];
-	QImage * bm = Header[Chan];
+	QImage * bm = Waterfall;
 
 	QPainter qPainter(bm);
 	qPainter.setBrush(Qt::black);
 	qPainter.setPen(Qt::white);
 
-	if (Chan == 0)
-		sprintf(Textxx, "Left");
-	else
-		sprintf(Textxx, "Right");
+	int Chan;
 
 #ifdef WIN32
-	int Top = 3;
+		int Top = 3;
 #else
-	int Top = 4;
+		int Top = 4;
 #endif
+		int Base = 0;
 
-	qPainter.drawText(2, Top, 100, 20, 0, Textxx);
-
-	// We drew markers every 100 Hz or 100 / binsize pixels
-
-
-	int Markers = ((WaterfallMax - WaterfallMin) / 100) + 5;			// Number of Markers to draw
-	int Freq = WaterfallMin;
-	float PixelsPerMarker = 100.0 / BinSize;
-
-
-
-	for (i = 0; i < Markers; i++)
-	{
-		x = round(PixelsPerMarker * i);
-		if (x < 1025)
+		for (Chan = 0; Chan < 2; Chan++)
 		{
-			if ((Freq % 500) == 0)
-				qPainter.drawLine(x, 22, x, 15);
+			if (Chan == 1 || ((UsingBothChannels == 0) && (UsingRight == 1)))
+				sprintf(Textxx, "Right");
 			else
-				qPainter.drawLine(x, 22, x, 18);
+				sprintf(Textxx, "Left");
 
-			if ((Freq % 500) == 0)
+			qPainter.drawText(2, Top, 100, 20, 0, Textxx);
+
+			// We drew markers every 100 Hz or 100 / binsize pixels
+
+			int Markers = ((WaterfallMax - WaterfallMin) / 100) + 5;			// Number of Markers to draw
+			int Freq = WaterfallMin;
+			float PixelsPerMarker = 100.0 / BinSize;
+
+			for (i = 0; i < Markers; i++)
 			{
-				sprintf(Textxx, "%d", Freq);
+				x = round(PixelsPerMarker * i);
+				if (x < 1025)
+				{
+					if ((Freq % 500) == 0)
+						qPainter.drawLine(x, Base + 22, x, Base + 15);
+					else
+						qPainter.drawLine(x, Base + 22, x, Base + 18);
 
-				if (x < 924)
-					qPainter.drawText(x - 12, Top, 100, 20, 0, Textxx);
+					if ((Freq % 500) == 0)
+					{
+						sprintf(Textxx, "%d", Freq);
+
+						if (x < 924)
+							qPainter.drawText(x - 12, Top, 100, 20, 0, Textxx);
+					}
+				}
+				Freq += 100;
 			}
+
+			if (UsingBothChannels == 0)
+				break;
+
+			Top += WaterfallTotalPixels;
+			Base = WaterfallTotalPixels;
 		}
-		Freq += 100;
-	}
-	HeaderCopy[Chan]->setPixmap(QPixmap::fromImage(*bm));
 
 }
 
-// This draws the frequency Markers on the Waterfall
+// These draws the frequency Markers on the Waterfall
 
-
-void do_pointer(int waterfall)
+void DrawModemFreqRange()
 {
 	if (nonGUIMode)
 		return;
 
+	// Draws the modem freq bars on waterfall header(s)
+
 
 	int x1, x2, k, pos1, pos2, pos3;
-	QImage * bm = Header[waterfall];
+	QImage * bm = Waterfall;
 
 	QPainter qPainter(bm);
 	qPainter.setBrush(Qt::NoBrush);
 	qPainter.setPen(Qt::white);
 
-	//	bm->fill(black);
+	int Chan;
+	int LRtoDisplay = LEFT;
+	int top = 0;
 
-	qPainter.fillRect(0, 23, 1024, 10, Qt::black);
-
-	// We drew markers every 100 Hz or 100 / binsize pixels
-
-	float PixelsPerHz = 1.0 / BinSize;
-	k = 26;
-
-	// draw all enabled ports on the ports on this soundcard
-
-	// First Modem is always on the first waterfall
-	// If second is enabled it is on the first unless different
-	//		channel from first
-
-	for (int i = 0; i < 4; i++)
+	for (Chan = 0; Chan < 2; Chan++)
 	{
+		if (Chan == 1 || ((UsingBothChannels == 0) && (UsingRight == 1)))
+			LRtoDisplay = RIGHT;
+
+		//	bm->fill(black);
+
+	//	qPainter.fillRect(top, 23, 1024, 10, Qt::black);
+
+		// We drew markers every 100 Hz or 100 / binsize pixels
+
+		float PixelsPerHz = 1.0 / BinSize;
+		k = 26 + top;
+
+		// draw all enabled ports on the ports on this soundcard
+
+		// First Modem is always on the first waterfall
+		// If second is enabled it is on the first unless different
+		//		channel from first
+
+		for (int i = 0; i < 4; i++)
+		{
+			if (soundChannel[i] != LRtoDisplay)
+					continue;
+
+			pos1 = roundf((((rxOffset + chanOffset[i] + rx_freq[i]) - 0.5*rx_shift[i]) - WaterfallMin) * PixelsPerHz) - 5;
+			pos2 = roundf((((rxOffset + chanOffset[i] + rx_freq[i]) + 0.5*rx_shift[i]) - WaterfallMin) * PixelsPerHz) - 5;
+			pos3 = roundf(((rxOffset + chanOffset[i] + rx_freq[i])) - WaterfallMin * PixelsPerHz);
+			x1 = pos1 + 5;
+			x2 = pos2 + 5;
+
+			qPainter.setPen(Qt::white);
+			qPainter.drawLine(x1, k, x2, k);
+			qPainter.drawLine(x1, k - 3, x1, k + 3);
+			qPainter.drawLine(x2, k - 3, x2, k + 3);
+			//		qPainter.drawLine(pos3, k - 3, pos3, k + 3);
+
+			if (rxOffset || chanOffset[i])
+			{
+				// Draw TX posn if rxOffset used
+
+				pos3 = roundf((rx_freq[i] - WaterfallMin) * PixelsPerHz);
+				qPainter.setPen(Qt::magenta);
+				qPainter.drawLine(pos3, k - 3, pos3, k + 3);
+				qPainter.drawLine(pos3, k - 3, pos3, k + 3);
+				qPainter.drawLine(pos3 - 2, k - 3, pos3 + 2, k - 3);
+			}
+
+			k += 3;
+		}
 		if (UsingBothChannels == 0)
-		{
-			// Only One Waterfall. If first chan is 
+			break;
 
-			if ((waterfall == 0 && soundChannel[i] == RIGHT) || (waterfall == 1 && soundChannel[i] == LEFT))
-				return;
-		}
-
-		if (soundChannel[i] == 0)
-			continue;
-
-
-		if (UsingBothChannels == 1)
-			if ((waterfall == 0 && soundChannel[i] == RIGHT) || (waterfall == 1 && soundChannel[i] == LEFT))
-				continue;
-
-		pos1 = roundf((((rxOffset + chanOffset[i] + rx_freq[i]) - 0.5*rx_shift[i]) - WaterfallMin) * PixelsPerHz) - 5;
-		pos2 = roundf((((rxOffset + chanOffset[i] + rx_freq[i]) + 0.5*rx_shift[i]) - WaterfallMin) * PixelsPerHz) - 5;
-		pos3 = roundf(((rxOffset + chanOffset[i] + rx_freq[i])) - WaterfallMin  * PixelsPerHz);
-		x1 = pos1 + 5;
-		x2 = pos2 + 5;
-
-		qPainter.setPen(Qt::white);
-		qPainter.drawLine(x1, k, x2, k);
-		qPainter.drawLine(x1, k - 3, x1, k + 3);
-		qPainter.drawLine(x2, k - 3, x2, k + 3);
-		qPainter.drawLine(pos3, k - 3, pos3, k + 3);
-
-		if (rxOffset || chanOffset[i])
-		{
-			// Draw TX posn if rxOffset used
-
-			pos3 = roundf((rx_freq[i] - WaterfallMin) * PixelsPerHz);
-			qPainter.setPen(Qt::magenta);
-			qPainter.drawLine(pos3, k - 3, pos3, k + 3);
-			qPainter.drawLine(pos3, k - 3, pos3, k + 3);
-			qPainter.drawLine(pos3 - 2, k - 3, pos3 + 2, k - 3);
-		}
-
-		k += 3;
+		LRtoDisplay = RIGHT;
+		top = WaterfallTotalPixels;
 	}
-	HeaderCopy[waterfall]->setPixmap(QPixmap::fromImage(*bm));
-}
-
-void wf_pointer(int snd_ch)
-{
-	UNUSED(snd_ch);
-
-	do_pointer(0);
-	do_pointer(1);
-//	do_pointer(2);
-//	do_pointer(3);
 }
 
 
 void doWaterfallThread(void * param);
 
-/*
-#ifdef WIN32
-
-#define pthread_t uintptr_t
-
-extern "C" uintptr_t _beginthread(void(__cdecl *start_address)(void *), unsigned stack_size, void *arglist);
-
-#else
-
-#include <pthread.h>
-
-extern "C" pthread_t _beginthread(void(*start_address)(void *), unsigned stack_size, void * arglist)
-{
-	pthread_t thread;
-
-	if (pthread_create(&thread, NULL, (void * (*)(void *))start_address, (void*)arglist) != 0)
-		perror("New Thread");
-	else
-		pthread_detach(thread);
-
-	return thread;
-}
-
-#endif
-*/
 extern "C" void doWaterfall(int snd_ch)
 {
 	if (nonGUIMode)
@@ -2934,6 +2824,20 @@ extern "C" void doWaterfall(int snd_ch)
 
 }
 
+extern "C" void displayWaterfall()
+{
+	// if we are using both channels but only want right need to extract correct half of Image
+
+	if (Waterfall == nullptr)
+		return;
+
+	if (UsingBothChannels && (Firstwaterfall == 0))
+		WaterfallCopy->setAlignment(Qt::AlignBottom | Qt::AlignLeft);
+	else
+		WaterfallCopy->setAlignment(Qt::AlignTop | Qt::AlignLeft);
+
+	WaterfallCopy->setPixmap(QPixmap::fromImage(*Waterfall));
+}
 
 extern "C" float aFFTAmpl[1024];
 extern "C" void SMUpdateBusyDetector(int LR, float * Real, float *Imag);
@@ -2941,7 +2845,6 @@ extern "C" void SMUpdateBusyDetector(int LR, float * Real, float *Imag);
 void doWaterfallThread(void * param)
 {
 	int snd_ch = (int)(size_t)param;
-	int WaterfallNumber = snd_ch;
 
 	if (lockWaterfall)
 		return;
@@ -2949,8 +2852,8 @@ void doWaterfallThread(void * param)
 	if (snd_ch == 1 && UsingLeft == 0)	// Only using right
 		snd_ch = 0;						// Samples are in first buffer
 
-	QImage * bm = Waterfall[snd_ch];
-	
+	QImage * bm = Waterfall;
+
 	int  i;
 	single  mag;
 	UCHAR * p;
@@ -3007,7 +2910,7 @@ void doWaterfallThread(void * param)
 		}
 	}
 	else
-	{		
+	{
 		dofft(&fft_buf[snd_ch][0], RealOut, ImagOut);
 
 		//	FourierTransform(1024, &fft_buf[snd_ch][0], RealOut, ImagOut, 0);
@@ -3048,7 +2951,7 @@ void doWaterfallThread(void * param)
 
 	SMUpdateBusyDetector(snd_ch, RealOut, ImagOut);
 
-	// we always do fft so we can get centre freq and do busy detect. Bot only upodate waterfall if on display
+	// we always do fft so we can get centre freq and do busy detect. But only upodate waterfall if on display
 
 	if (bm == 0)
 		return;
@@ -3056,66 +2959,55 @@ void doWaterfallThread(void * param)
 	if ((Firstwaterfall == 0 && snd_ch == 0) || (Secondwaterfall == 0 && snd_ch == 1))
 		return;
 
-	try
+	p = Line;
+	lineLen = 4096;
+
+	if (raduga == DISP_MONO)
 	{
-
-		p = Line;
-		lineLen = 4096;
-
-		if (raduga == DISP_MONO)
+		for (i = Start; i < End; i++)
 		{
-			for (i = Start; i < End; i++)
-			{
-				n = fft_disp[snd_ch][i];
-				*(p++) = n;					// all colours the same
-				*(p++) = n;
-				*(p++) = n;
-				p++;
-			}
+			n = fft_disp[snd_ch][i];
+			*(p++) = n;					// all colours the same
+			*(p++) = n;
+			*(p++) = n;
+			p++;
 		}
-		else
-		{
-			for (i = Start; i < End; i++)
-			{
-				n = fft_disp[snd_ch][i];
-				memcpy(p, &RGBWF[n], 4);
-				p += 4;
-			}
-		}
-
-		// Scroll
-
-		int TopLine = NextWaterfallLine[snd_ch];
-
-		// Write line to cyclic buffer then draw starting with the line just written
-
-		memcpy(&WaterfallLines[snd_ch][NextWaterfallLine[snd_ch]++][0], Line, 4096);
-		if (NextWaterfallLine[snd_ch] > 79)
-			NextWaterfallLine[snd_ch] = 0;
-
-		for (int j = 79; j > 0; j--)
-		{
-			p = bm->scanLine(j);
-			memcpy(p, &WaterfallLines[snd_ch][TopLine][0], lineLen);
-			TopLine++;
-			if (TopLine > 79)
-				TopLine = 0;
-		}
-
-		WaterfallCopy[WaterfallNumber]->setPixmap(QPixmap::fromImage(*bm));
-		//	WaterfallCopy[snd_ch - 1]->setPixmap(*pm);
-			//	WaterfallCopy[1]->setPixmap(QPixmap::fromImage(*bm));
 	}
-	catch (const std::exception& e) // caught by reference to base
+	else
 	{
-		qDebug() << " a standard exception was caught, with message '"
-			<< e.what() << "'\n";
+		for (i = Start; i < End; i++)
+		{
+			n = fft_disp[snd_ch][i];
+			memcpy(p, &RGBWF[n], 4);
+			p += 4;
+		}
 	}
 
+	// Scroll
+
+	int TopLine = NextWaterfallLine[snd_ch];
+	int TopScanLine = WaterfallHeaderPixels;
+
+	if (snd_ch)
+		TopScanLine += WaterfallTotalPixels;
+
+	// Write line to cyclic buffer then draw starting with the line just written
+
+	memcpy(&WaterfallLines[snd_ch][NextWaterfallLine[snd_ch]++][0], Line, 4096);
+	if (NextWaterfallLine[snd_ch] > 79)
+		NextWaterfallLine[snd_ch] = 0;
+
+	for (int j = 79; j > 0; j--)
+	{
+		p = bm->scanLine(j + TopScanLine);
+		memcpy(p, &WaterfallLines[snd_ch][TopLine][0], lineLen);
+		TopLine++;
+		if (TopLine > 79)
+			TopLine = 0;
+	}
 }
 
 
-
 void QtSoundModem::changeEvent(QEvent* e)
 {
 	if (e->type() == QEvent::WindowStateChange)
diff --git a/QtSoundModem.cpp.bak b/QtSoundModem.cpp.bak
deleted file mode 100644
index 3efef28..0000000
--- a/QtSoundModem.cpp.bak
+++ /dev/null
@@ -1,2866 +0,0 @@
-/*
-Copyright (C) 2019-2020 Andrei Kopanchuk UZ7HO
-
-This file is part of QtSoundModem
-
-QtSoundModem is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-QtSoundModem is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with QtSoundModem.  If not, see http://www.gnu.org/licenses
-
-*/
-
-// UZ7HO Soundmodem Port by John Wiseman G8BPQ
-
-// UZ7HO Soundmodem Port
-
-// Not Working 4psk100 FEC 
-
-// Thoughts on Waterfall Display.
-
-// Original used a 2048 sample FFT giving 5.859375 Hz bins. We plotted 1024 points, giving a 0 to 6000 specrum
-
-// If we want say 300 to 3300 we need about half the bin size so twice the fft size. But should we also fit required range to window size?
-
-// Unless we resize the most displayed bit of the screen in around 900 pixels. So each bin should be 3300 / 900 = 3.66667 Hz or a FFT size of around 3273
-
-#include "QtSoundModem.h"
-#include <qheaderview.h>
-//#include <QDebug>
-#include <QHostAddress>
-#include <QAbstractSocket>
-#include <QSettings>
-#include <QPainter>
-#include <QtSerialPort/QSerialPort>
-#include <QtSerialPort/QSerialPortInfo>
-#include <QMessageBox>
-#include <QTimer>
-#include <qevent.h>
-#include <QStandardItemModel>
-#include <QScrollBar>
-
-#include "UZ7HOStuff.h"
-
-
-QImage *Constellation;
-QImage *Waterfall[4] = { 0,0,0,0 };
-QImage *Header[4];
-QLabel *DCDLabel[4];
-QLineEdit *chanOffsetLabel[4];
-QImage *DCDLed[4];
-
-QImage *RXLevel;
-
-QLabel *WaterfallCopy[2];
-QLabel *HeaderCopy[2];
-
-QTextEdit * monWindowCopy;
-
-extern workerThread *t;
-extern QtSoundModem * w;
-
-QList<QSerialPortInfo> Ports = QSerialPortInfo::availablePorts();
-
-void saveSettings();
-void getSettings();
-extern "C" void CloseSound();
-extern "C" void GetSoundDevices();
-extern "C" char modes_name[modes_count][20];
-extern "C" int speed[5];
-extern "C" int KISSPort;
-extern "C" short rx_freq[5];
-
-extern "C" int CaptureCount;
-extern "C" int PlaybackCount;
-
-extern "C" int CaptureIndex;		// Card number
-extern "C" int PlayBackIndex;
-
-extern "C" char CaptureNames[16][256];
-extern "C" char PlaybackNames[16][256];
-
-extern "C" int SoundMode;
-extern "C" int multiCore;
-
-extern "C" int refreshModems;
-
-extern "C" int pnt_change[5];
-extern "C" int needRSID[4];
-
-extern "C" int needSetOffset[4];
-
-extern "C" float MagOut[4096];
-extern "C" float MaxMagOut;
-extern "C" int MaxMagIndex;
-
-extern "C"
-{ 
-	int InitSound(BOOL Report);
-	void soundMain();
-	void MainLoop();
-	void modulator(UCHAR snd_ch, int buf_size);
-	void SampleSink(int LR, short Sample);
-	void doCalib(int Port, int Act);
-	int Freq_Change(int Chan, int Freq);
-	void set_speed(int snd_ch, int Modem);
-	void init_speed(int snd_ch);
-	void wf_pointer(int snd_ch);
-	void FourierTransform(int NumSamples, short * RealIn, float * RealOut, float * ImagOut, int InverseTransform);
-	void dofft(short * in, float * outr, float * outi);
-	void init_raduga();
-	void wf_Scale(int Chan);
-	void AGW_Report_Modem_Change(int port);
-	char * strlop(char * buf, char delim);
-	void sendRSID(int Chan, int dropTX);
-	void RSIDinitfft();
-	void il2p_init(int il2p_debug);
-}
-
-void make_graph_buf(float * buf, short tap, QPainter * bitmap);
-
-int ModemA = 2;
-int ModemB = 2;
-int ModemC = 2;
-int ModemD = 2;
-int FreqA = 1500;
-int FreqB = 1500;
-int FreqC = 1500;
-int FreqD = 1500;
-int DCD = 50;
-
-char CWIDCall[128] = "";
-int CWIDInterval = 0;
-int CWIDLeft = 0;
-int CWIDRight = 0;
-int CWIDType = 1;			// on/off
-
-extern "C" { int RSID_SABM[4]; }
-extern "C" { int RSID_UI[4]; }
-extern "C" { int RSID_SetModem[4]; }
-
-int Closing = FALSE;				// Set to stop background thread
-
-QRgb white = qRgb(255, 255, 255);
-QRgb black = qRgb(0, 0, 0);
-
-QRgb green = qRgb(0, 255, 0);
-QRgb red = qRgb(255, 0, 0);
-QRgb yellow = qRgb(255, 255, 0);
-QRgb cyan = qRgb(0, 255, 255);
-
-// Indexed colour list from ARDOPC
-
-#define WHITE 0
-#define Tomato 1
-#define Gold 2
-#define Lime 3
-#define Yellow 4
-#define Orange 5
-#define Khaki 6
-#define Cyan 7
-#define DeepSkyBlue 8
-#define RoyalBlue 9
-#define Navy 10
-#define Black 11
-#define Goldenrod 12
-#define Fuchsia 13
-
-QRgb vbColours[16] = { qRgb(255, 255, 255), qRgb(255, 99, 71), qRgb(255, 215, 0), qRgb(0, 255, 0),
-						qRgb(255, 255, 0), qRgb(255, 165, 0), qRgb(240, 240, 140), qRgb(0, 255, 255),
-						qRgb(0, 191, 255), qRgb(65, 105, 225), qRgb(0, 0, 128), qRgb(0, 0, 0),
-						qRgb(218, 165, 32), qRgb(255, 0, 255) };
-
-unsigned char  WaterfallLines[2][80][4096] = { 0 };
-int NextWaterfallLine[2] = { 0 };
-
-unsigned int LastLevel = 255;
-unsigned int LastBusy = 255;
-
-extern "C" int UDPClientPort;
-extern "C" int UDPServerPort;
-extern "C" int TXPort;
-extern char UDPHost[64];
-
-QTimer *cwidtimer;
-
-QSystemTrayIcon * trayIcon = nullptr;
-
-int MintoTray = 1;
-
-int RSID_WF = 0;				// Set to use RSID FFT for Waterfall. 
-
-extern "C" void WriteDebugLog(char * Mess)
-{
-	qDebug() << Mess;
-}
-
-void QtSoundModem::doupdateDCD(int Chan, int State)
-{
-	DCDLabel[Chan]->setVisible(State);
-}
-
-extern "C" char * frame_monitor(string * frame, char * code, bool tx_stat);
-extern "C" char * ShortDateTime();
-
-extern "C" void mon_rsid(int snd_ch, char * RSID)
-{
-	int Len;
-	char * Msg = (char *)malloc(1024);		// Cant pass local variable via signal/slot
-
-	sprintf(Msg, "%d:%s [%s%c]", snd_ch + 1, RSID, ShortDateTime(), 'R');
-
-	Len = strlen(Msg);
-
-	if (Msg[Len - 1] != '\r')
-	{
-		Msg[Len++] = '\r';
-		Msg[Len] = 0;
-	}
-
-	emit t->sendtoTrace(Msg, 0);
-}
-
-extern "C" void put_frame(int snd_ch, string * frame, char * code, int  tx, int excluded)
-{
-	UNUSED(excluded);
-
-	int Len;
-	char * Msg = (char *)malloc(1024);		// Cant pass local variable via signal/slot
-
-	if (strcmp(code, "NON-AX25") == 0)
-		sprintf(Msg, "%d: <NON-AX25 frame Len = %d [%s%c]\r", snd_ch, frame->Length, ShortDateTime(), 'R');
-	else
-		sprintf(Msg, "%d:%s", snd_ch + 1, frame_monitor(frame, code, tx));
-
-	Len = strlen(Msg);
-
-	if (Msg[Len - 1] != '\r')
-	{
-		Msg[Len++] = '\r';
-		Msg[Len] = 0;
-	}
-
-	emit t->sendtoTrace(Msg, tx);
-}
-
-extern "C" void updateDCD(int Chan, bool State)
-{
-	emit t->updateDCD(Chan, State);
-}
-
-bool QtSoundModem::eventFilter(QObject* obj, QEvent *evt)
-{
-	UNUSED(obj);
-
-	if (evt->type() == QEvent::Resize)
-	{
-		return QWidget::event(evt);
-	}
-
-	if (evt->type() == QEvent::WindowStateChange)
-	{
-		if (windowState().testFlag(Qt::WindowMinimized) == true)
-			w_state = WIN_MINIMIZED;
-		else
-			w_state = WIN_MAXIMIZED;
-	}
-//	if (evt->type() == QGuiApplication::applicationStateChanged) - this is a sigma;
-//	{
-//		qDebug() << "App State changed =" << evt->type() << endl;
-//	}
-
-	return QWidget::event(evt);
-}
-
-void QtSoundModem::resizeEvent(QResizeEvent* event)
-{
-	QMainWindow::resizeEvent(event);
-
-	QRect r = geometry();
-
-	int A, B, C, W;
-	int modemBoxHeight = 30;
-
-	ui.modeB->setVisible(soundChannel[1]);
-	ui.centerB->setVisible(soundChannel[1]);
-	ui.labelB->setVisible(soundChannel[1]);
-	DCDLabel[1]->setVisible(soundChannel[1]);
-	ui.RXOffsetB->setVisible(soundChannel[1]);
-
-	ui.modeC->setVisible(soundChannel[2]);
-	ui.centerC->setVisible(soundChannel[2]);
-	ui.labelC->setVisible(soundChannel[2]);
-	DCDLabel[2]->setVisible(soundChannel[2]);
-	ui.RXOffsetC->setVisible(soundChannel[2]);
-
-	ui.modeD->setVisible(soundChannel[3]);
-	ui.centerD->setVisible(soundChannel[3]);
-	ui.labelD->setVisible(soundChannel[3]);
-	DCDLabel[3]->setVisible(soundChannel[3]);
-	ui.RXOffsetD->setVisible(soundChannel[3]);
-
-	if (soundChannel[2] || soundChannel[3])
-		modemBoxHeight = 60;
-
-
-	A = r.height() - 25;   // No waterfalls
-
-	if (UsingBothChannels && Secondwaterfall)
-	{
-		// Two waterfalls
-
-		ui.WaterfallA->setVisible(1);
-		ui.HeaderA->setVisible(1);
-		ui.WaterfallB->setVisible(1);
-		ui.HeaderB->setVisible(1);
-
-		A = r.height() - 258;   // Top of Waterfall A
-		B = A + 115;			// Top of Waterfall B
-	}
-	else
-	{
-		// One waterfall
-
-		// Could be Left or Right
-
-		if (Firstwaterfall)
-		{
-			if (soundChannel[0] == RIGHT)
-			{
-				ui.WaterfallA->setVisible(0);
-				ui.HeaderA->setVisible(0);
-				ui.WaterfallB->setVisible(1);
-				ui.HeaderB->setVisible(1);
-			}
-			else
-			{
-				ui.WaterfallA->setVisible(1);
-				ui.HeaderA->setVisible(1);
-				ui.WaterfallB->setVisible(0);
-				ui.HeaderB->setVisible(0);
-			}
-
-			A = r.height() - 145;   // Top of Waterfall A
-		}
-		else
-			A = r.height() - 25;   // Top of Waterfall A
-	}
-
-	C = A - 150;			// Bottom of Monitor, Top of connection list
-	W = r.width();
-
-	// Calc Positions of Waterfalls
-
-	ui.monWindow->setGeometry(QRect(0, modemBoxHeight, W, C - (modemBoxHeight + 26)));
-	sessionTable->setGeometry(QRect(0, C, W, 175));
-
-	if (UsingBothChannels)
-	{
-		ui.HeaderA->setGeometry(QRect(0, A, W, 35));
-		ui.WaterfallA->setGeometry(QRect(0, A + 35, W, 80));
-		ui.HeaderB->setGeometry(QRect(0, B, W, 35));
-		ui.WaterfallB->setGeometry(QRect(0, B + 35, W, 80));
-	}
-	else
-	{
-		if (soundChannel[0] == RIGHT)
-		{
-			ui.HeaderB->setGeometry(QRect(0, A, W, 35));
-			ui.WaterfallB->setGeometry(QRect(0, A + 35, W, 80));
-		}
-		else
-		{
-			ui.HeaderA->setGeometry(QRect(0, A, W, 35));
-			ui.WaterfallA->setGeometry(QRect(0, A + 35, W, 80));
-		}
-	}
-}
-
-QAction * setupMenuLine(QMenu * Menu, char * Label, QObject * parent, int State)
-{
-	QAction * Act = new QAction(Label, parent);
-	Menu->addAction(Act);
-
-	Act->setCheckable(true);
-	if (State)
-		Act->setChecked(true);
-
-	parent->connect(Act, SIGNAL(triggered()), parent, SLOT(menuChecked()));
-
-	return Act;
-}
-
-void QtSoundModem::menuChecked()
-{
-	QAction * Act = static_cast<QAction*>(QObject::sender());
-
-	int state = Act->isChecked();
-
-	if (Act == actWaterfall1)
-	{
-		int oldstate = Firstwaterfall;
-		Firstwaterfall = state;
-
-		if (state != oldstate)
-			initWaterfall(0, state);
-
-	}
-	else if (Act == actWaterfall2)
-	{
-		int oldstate = Secondwaterfall;
-		Secondwaterfall = state;
-
-		if (state != oldstate)
-			initWaterfall(1, state);
-
-	}
-	saveSettings();
-}
-
-void QtSoundModem::initWaterfall(int chan, int state)
-{
-	if (state == 1)
-	{
-		if (chan == 0)
-		{
-			ui.WaterfallA = new QLabel(ui.centralWidget);
-			WaterfallCopy[0] = ui.WaterfallA;
-		}
-		else
-		{
-			ui.WaterfallB = new QLabel(ui.centralWidget);
-			WaterfallCopy[1] = ui.WaterfallB;
-		}
-		Waterfall[chan] = new QImage(1024, 80, QImage::Format_RGB32);
-		Waterfall[chan]->fill(black);
-
-	}
-	else
-	{
-		delete(Waterfall[chan]);
-		Waterfall[chan] = 0;
-	}
-
-	QSize Size(800, 602);						// Not actually used, but Event constructor needs it
-	QResizeEvent *event = new QResizeEvent(Size, Size);
-	QApplication::sendEvent(this, event);
-}
-
-// Local copies
-
-QLabel *RXOffsetLabel;
-QSlider *RXOffset;
-
-QtSoundModem::QtSoundModem(QWidget *parent) : QMainWindow(parent)
-{
-	ui.setupUi(this);
-
-	QSettings mysettings("QtSoundModem.ini", QSettings::IniFormat);
-
-	if (MintoTray)
-	{
-		char popUp[256];
-		sprintf(popUp, "QtSoundModem %d %d", AGWPort, KISSPort);
-		trayIcon = new QSystemTrayIcon(QIcon(":/QtSoundModem/soundmodem.ico"), this);
-		trayIcon->setToolTip(popUp);
-		trayIcon->show();
-
-		connect(trayIcon, SIGNAL(activated(QSystemTrayIcon::ActivationReason)), this, SLOT(TrayActivated(QSystemTrayIcon::ActivationReason)));
-	}
-
-
-	restoreGeometry(mysettings.value("geometry").toByteArray());
-	restoreState(mysettings.value("windowState").toByteArray());
-
-	sessionTable = new QTableWidget(this);
-
-	sessionTable->verticalHeader()->setVisible(FALSE);
-	sessionTable->verticalHeader()->setDefaultSectionSize(20);
-	sessionTable->horizontalHeader()->setDefaultSectionSize(68);
-	sessionTable->setRowCount(1);
-	sessionTable->setColumnCount(12);
-	m_TableHeader << "MyCall" << "DestCall" << "Status" << "Sent pkts" << "Sent Bytes" << "Rcvd pkts" << "Rcvd bytes" << "Rcvd FC" << "FEC corr" << "CPS TX" << "CPS RX" << "Direction";
-
-	sessionTable->setStyleSheet("QHeaderView::section { background-color:rgb(224, 224, 224) }");
-
-	sessionTable->setHorizontalHeaderLabels(m_TableHeader);
-	sessionTable->setColumnWidth(0, 80);
-	sessionTable->setColumnWidth(1, 80);
-	sessionTable->setColumnWidth(4, 76);
-	sessionTable->setColumnWidth(5, 76);
-	sessionTable->setColumnWidth(6, 80);
-	sessionTable->setColumnWidth(11, 72);
-
-	for (int i = 0; i < modes_count; i++)
-	{
-		ui.modeA->addItem(modes_name[i]);
-		ui.modeB->addItem(modes_name[i]);
-		ui.modeC->addItem(modes_name[i]);
-		ui.modeD->addItem(modes_name[i]);
-	}
-
-	// Set up Menus
-
-	setupMenu = ui.menuBar->addMenu(tr("Settings"));
-
-	actDevices = new QAction("Setup Devices", this);
-	setupMenu->addAction(actDevices);
-
-	connect(actDevices, SIGNAL(triggered()), this, SLOT(clickedSlot()));
-	actDevices->setObjectName("actDevices");
-	actModems = new QAction("Setup Modems", this);
-	actModems->setObjectName("actModems");
-	setupMenu->addAction(actModems);
-
-	connect(actModems, SIGNAL(triggered()), this, SLOT(clickedSlot()));
-
-	actMintoTray = setupMenu->addAction("Minimize to Tray", this, SLOT(MinimizetoTray()));
-	actMintoTray->setCheckable(1);
-	actMintoTray->setChecked(MintoTray);
-
-	viewMenu = ui.menuBar->addMenu(tr("&View"));
-
-	actWaterfall1 = setupMenuLine(viewMenu, (char *)"First waterfall", this, Firstwaterfall);
-	actWaterfall2 = setupMenuLine(viewMenu, (char *)"Second Waterfall", this, Secondwaterfall);
-
-	actCalib = ui.menuBar->addAction("&Calibration");
-	connect(actCalib, SIGNAL(triggered()), this, SLOT(doCalibrate()));
-
-	actRestartWF = ui.menuBar->addAction("Restart Waterfall");
-	connect(actRestartWF, SIGNAL(triggered()), this, SLOT(doRestartWF()));
-
-	actAbout = ui.menuBar->addAction("&About");
-	connect(actAbout, SIGNAL(triggered()), this, SLOT(doAbout()));
-
-	//	Constellation = new QImage(91, 91, QImage::Format_RGB32);
-
-	Header[0] = new QImage(1024, 35, QImage::Format_RGB32);
-	Header[1] = new QImage(1024, 35, QImage::Format_RGB32);
-	RXLevel = new QImage(150, 10, QImage::Format_RGB32);
-
-	DCDLabel[0] = new QLabel(this);
-	DCDLabel[0]->setObjectName(QString::fromUtf8("DCDLedA"));
-	DCDLabel[0]->setGeometry(QRect(280, 31, 12, 12));
-	DCDLabel[0]->setVisible(TRUE);
-
-	DCDLabel[1] = new QLabel(this);
-	DCDLabel[1]->setObjectName(QString::fromUtf8("DCDLedB"));
-	DCDLabel[1]->setGeometry(QRect(575, 31, 12, 12));
-	DCDLabel[1]->setVisible(TRUE);
-
-	DCDLabel[2] = new QLabel(this);
-	DCDLabel[2]->setObjectName(QString::fromUtf8("DCDLedC"));
-	DCDLabel[2]->setGeometry(QRect(280, 61, 12, 12));
-	DCDLabel[2]->setVisible(FALSE);
-
-	DCDLabel[3] = new QLabel(this);
-	DCDLabel[3]->setObjectName(QString::fromUtf8("DCDLedD"));
-	DCDLabel[3]->setGeometry(QRect(575, 61, 12, 12));
-	DCDLabel[3]->setVisible(FALSE);
-	
-	DCDLed[0] = new QImage(12, 12, QImage::Format_RGB32);
-	DCDLed[1] = new QImage(12, 12, QImage::Format_RGB32);
-	DCDLed[2] = new QImage(12, 12, QImage::Format_RGB32);
-	DCDLed[3] = new QImage(12, 12, QImage::Format_RGB32);
-
-	DCDLed[0]->fill(red);
-	DCDLed[1]->fill(red);
-	DCDLed[2]->fill(red);
-	DCDLed[3]->fill(red);
-
-	DCDLabel[0]->setPixmap(QPixmap::fromImage(*DCDLed[0]));
-	DCDLabel[1]->setPixmap(QPixmap::fromImage(*DCDLed[1]));
-	DCDLabel[2]->setPixmap(QPixmap::fromImage(*DCDLed[2]));
-	DCDLabel[3]->setPixmap(QPixmap::fromImage(*DCDLed[3]));
-
-	chanOffsetLabel[0] = ui.RXOffsetA;
-	chanOffsetLabel[1] = ui.RXOffsetB;
-	chanOffsetLabel[2] = ui.RXOffsetC;
-	chanOffsetLabel[3] = ui.RXOffsetD;
-
-
-	//	Waterfall[0]->setColorCount(16);
-	//	Waterfall[1]->setColorCount(16);
-
-
-	//	for (i = 0; i < 16; i++)
-	//	{
-	//	Waterfall[0]->setColor(i, vbColours[i]);
-	//		Waterfall[1]->setColor(i, vbColours[i]);
-	//	}
-
-	WaterfallCopy[0] = ui.WaterfallA;
-	WaterfallCopy[1] = ui.WaterfallB;
-
-	initWaterfall(0, 1);
-	initWaterfall(1, 1);
-
-	Header[0]->fill(black);
-	Header[1]->fill(black);
-
-	HeaderCopy[0] = ui.HeaderA;
-	HeaderCopy[1] = ui.HeaderB;
-	monWindowCopy = ui.monWindow;
-
-	ui.monWindow->document()->setMaximumBlockCount(10000);
-
-//	connect(ui.monWindow, SIGNAL(selectionChanged()), this, SLOT(onTEselectionChanged()));
-
-	ui.HeaderA->setPixmap(QPixmap::fromImage(*Header[0]));
-	ui.HeaderB->setPixmap(QPixmap::fromImage(*Header[1]));
-
-	wf_pointer(soundChannel[0]);
-	wf_pointer(soundChannel[1]);
-	wf_Scale(0);
-	wf_Scale(1);
-
-	//	RefreshLevel(0);
-	//	RXLevel->setPixmap(QPixmap::fromImage(*RXLevel));
-
-	connect(ui.modeA, SIGNAL(currentIndexChanged(int)), this, SLOT(clickedSlotI(int)));
-	connect(ui.modeB, SIGNAL(currentIndexChanged(int)), this, SLOT(clickedSlotI(int)));
-	connect(ui.modeC, SIGNAL(currentIndexChanged(int)), this, SLOT(clickedSlotI(int)));
-	connect(ui.modeD, SIGNAL(currentIndexChanged(int)), this, SLOT(clickedSlotI(int)));
-
-	ui.modeA->setCurrentIndex(speed[0]);
-	ui.modeB->setCurrentIndex(speed[1]);
-	ui.modeC->setCurrentIndex(speed[2]);
-	ui.modeD->setCurrentIndex(speed[3]);
-
-	ModemA = ui.modeA->currentIndex();
-
-	ui.centerA->setValue(rx_freq[0]);
-	ui.centerB->setValue(rx_freq[1]);
-	ui.centerC->setValue(rx_freq[2]);
-	ui.centerD->setValue(rx_freq[3]);
-
-	connect(ui.centerA, SIGNAL(valueChanged(int)), this, SLOT(clickedSlotI(int)));
-	connect(ui.centerB, SIGNAL(valueChanged(int)), this, SLOT(clickedSlotI(int)));
-	connect(ui.centerC, SIGNAL(valueChanged(int)), this, SLOT(clickedSlotI(int)));
-	connect(ui.centerD, SIGNAL(valueChanged(int)), this, SLOT(clickedSlotI(int)));
-
-	ui.DCDSlider->setValue(dcd_threshold);
-
-
-	char valChar[32];
-	sprintf(valChar, "RX Offset %d", rxOffset);
-	ui.RXOffsetLabel->setText(valChar);
-	ui.RXOffset->setValue(rxOffset);
-
-	RXOffsetLabel = ui.RXOffsetLabel;
-	RXOffset = ui.RXOffset;
-
-	connect(ui.DCDSlider, SIGNAL(sliderMoved(int)), this, SLOT(clickedSlotI(int)));
-	connect(ui.RXOffset, SIGNAL(valueChanged(int)), this, SLOT(clickedSlotI(int)));
-
-
-	QObject::connect(t, SIGNAL(sendtoTrace(char *, int)), this, SLOT(sendtoTrace(char *, int)), Qt::QueuedConnection);
-	QObject::connect(t, SIGNAL(updateDCD(int, int)), this, SLOT(doupdateDCD(int, int)), Qt::QueuedConnection);
-
-	connect(ui.RXOffsetA, SIGNAL(returnPressed()), this, SLOT(returnPressed()));
-	connect(ui.RXOffsetB, SIGNAL(returnPressed()), this, SLOT(returnPressed()));
-	connect(ui.RXOffsetC, SIGNAL(returnPressed()), this, SLOT(returnPressed()));
-	connect(ui.RXOffsetD, SIGNAL(returnPressed()), this, SLOT(returnPressed()));
-
-	QTimer *timer = new QTimer(this);
-	connect(timer, SIGNAL(timeout()), this, SLOT(MyTimerSlot()));
-	timer->start(100);
-
-
-	cwidtimer = new QTimer(this);
-	connect(cwidtimer, SIGNAL(timeout()), this, SLOT(CWIDTimer()));
-
-	if (CWIDInterval)
-		cwidtimer->start(CWIDInterval * 60000);
-
-	if (RSID_SetModem[0])
-	{
-		RSID_WF = 1;
-		RSIDinitfft();
-	}
-	il2p_init(1);
-}
-
-void QtSoundModem::MinimizetoTray()
-{
-	MintoTray = actMintoTray->isChecked();
-	saveSettings();
-	QMessageBox::about(this, tr("QtSoundModem"),
-	tr("Program must be restarted to change Minimize mode"));
-}
-
-
-void QtSoundModem::TrayActivated(QSystemTrayIcon::ActivationReason reason)
-{
-	if (reason == 3)
-	{
-		showNormal();
-		w->setWindowState((w->windowState() & ~Qt::WindowMinimized) | Qt::WindowActive);
-	} 
-}
-
-extern "C" void sendCWID(char * strID, BOOL blnPlay, int Chan);
-
-void QtSoundModem::CWIDTimer()
-{
-	sendCWID(CWIDCall, CWIDType, 0);
-	calib_mode[0] = 4;
-}
-
-void extSetOffset(int chan)
-{
-	char valChar[32];
-	sprintf(valChar, "%d", chanOffset[chan]);
-	chanOffsetLabel[chan]->setText(valChar);
-
-	wf_pointer(soundChannel[chan]);
-
-	pnt_change[0] = 1;
-	pnt_change[1] = 1;
-	pnt_change[2] = 1;
-	pnt_change[3] = 1;
-
-	return;
-}
-	
-void QtSoundModem::MyTimerSlot()
-{
-	// 100 mS Timer Event
-
-	for (int i = 0; i < 4; i++)
-	{
-
-		if (needSetOffset[i])
-		{
-			needSetOffset[i] = 0;
-			extSetOffset(i);						// Update GUI
-		}
-	}
-
-	if (refreshModems)
-	{
-		refreshModems = 0;
-
-		ui.modeA->setCurrentIndex(speed[0]);
-		ui.modeB->setCurrentIndex(speed[1]);
-		ui.modeC->setCurrentIndex(speed[2]);
-		ui.modeD->setCurrentIndex(speed[3]);
-		ui.centerA->setValue(rx_freq[0]);
-		ui.centerB->setValue(rx_freq[1]);
-		ui.centerC->setValue(rx_freq[2]);
-		ui.centerD->setValue(rx_freq[3]);
-	}
-
-	show_grid();
-}
-
-void QtSoundModem::returnPressed()
-{
-	char Name[32];
-	int Chan;
-	QString val;
-	
-	strcpy(Name, sender()->objectName().toUtf8());
-
-	Chan = Name[8] - 'A';
-
-	val = chanOffsetLabel[Chan]->text();
-
-	chanOffset[Chan] = val.toInt();
-	needSetOffset[Chan] = 1;				// Update GUI
-
-
-}
-
-
-void QtSoundModem::clickedSlotI(int i)
-{
-	char Name[32];
-
-	strcpy(Name, sender()->objectName().toUtf8());
-
-	if (strcmp(Name, "modeA") == 0)
-	{
-		ModemA = ui.modeA->currentIndex();
-		set_speed(0, ModemA);
-		saveSettings();
-		AGW_Report_Modem_Change(0);
-		return;
-	}
-
-	if (strcmp(Name, "modeB") == 0)
-	{
-		ModemB = ui.modeB->currentIndex();
-		set_speed(1, ModemB);
-		saveSettings();
-		AGW_Report_Modem_Change(1);
-		return;
-	}
-
-	if (strcmp(Name, "modeC") == 0)
-	{
-		ModemC = ui.modeC->currentIndex();
-		set_speed(2, ModemC);
-		saveSettings();
-		AGW_Report_Modem_Change(2);
-		return;
-	}
-
-	if (strcmp(Name, "modeD") == 0)
-	{
-		ModemD = ui.modeD->currentIndex();
-		set_speed(3, ModemD);
-		saveSettings();
-		AGW_Report_Modem_Change(3);
-		return;
-	}
-
-	if (strcmp(Name, "centerA") == 0)
-	{
-		if (i > 300)
-		{
-			QSettings * settings = new QSettings("QtSoundModem.ini", QSettings::IniFormat);
-			ui.centerA->setValue(Freq_Change(0, i));
-			settings->setValue("Modem/RXFreq1", ui.centerA->value());
-			AGW_Report_Modem_Change(0);
-
-		}
-		return;
-	}
-
-	if (strcmp(Name, "centerB") == 0)
-	{
-		if (i > 300)
-		{
-			QSettings * settings = new QSettings("QtSoundModem.ini", QSettings::IniFormat);
-			ui.centerB->setValue(Freq_Change(1, i));
-			settings->setValue("Modem/RXFreq2", ui.centerB->value());
-			AGW_Report_Modem_Change(1);
-		}
-		return;
-	}
-
-	if (strcmp(Name, "centerC") == 0)
-	{
-		if (i > 300)
-		{
-			QSettings * settings = new QSettings("QtSoundModem.ini", QSettings::IniFormat);
-			ui.centerC->setValue(Freq_Change(2, i));
-			settings->setValue("Modem/RXFreq3", ui.centerC->value());
-			AGW_Report_Modem_Change(2);
-		}
-		return;
-	}
-
-	if (strcmp(Name, "centerD") == 0)
-	{
-		if (i > 300)
-		{
-			QSettings * settings = new QSettings("QtSoundModem.ini", QSettings::IniFormat);
-			ui.centerD->setValue(Freq_Change(3, i));
-			settings->setValue("Modem/RXFreq4", ui.centerD->value());
-			AGW_Report_Modem_Change(3);
-		}
-		return;
-	}
-
-	if (strcmp(Name, "DCDSlider") == 0)
-	{
-		dcd_threshold = i;
-		saveSettings();
-		return;
-	}
-	
-	if (strcmp(Name, "RXOffset") == 0)
-	{
-		char valChar[32];
-		rxOffset = i;
-		sprintf(valChar, "RX Offset %d",rxOffset);
-		ui.RXOffsetLabel->setText(valChar);
-
-		wf_pointer(soundChannel[0]);
-		wf_pointer(soundChannel[1]);
-
-		pnt_change[0] = 1;
-		pnt_change[1] = 1;
-		pnt_change[2] = 1;
-		pnt_change[3] = 1;
-
-		saveSettings();
-		return;
-	}
-
-
-	QMessageBox msgBox;
-	msgBox.setWindowTitle("MessageBox Title");
-	msgBox.setText("You Clicked " + ((QPushButton*)sender())->objectName());
-	msgBox.exec();
-}
-
-
-void QtSoundModem::clickedSlot()
-{
-	char Name[32];
-
-	strcpy(Name, sender()->objectName().toUtf8());
-
-	if (strcmp(Name, "actDevices") == 0)
-	{
-		doDevices();
-		return;
-	}
-
-	if (strcmp(Name, "actModems") == 0)
-	{
-		doModems();
-		return;
-	}
-
-	if (strcmp(Name, "showBPF_A") == 0)
-	{
-		doFilter(0, 0);
-		return;
-	}
-
-	if (strcmp(Name, "showTXBPF_A") == 0)
-	{
-		doFilter(0, 1);
-		return;
-	}
-
-	if (strcmp(Name, "showLPF_A") == 0)
-	{
-		doFilter(0, 2);
-		return;
-	}
-	
-
-	if (strcmp(Name, "showBPF_B") == 0)
-	{
-		doFilter(1, 0);
-		return;
-	}
-
-	if (strcmp(Name, "showTXBPF_B") == 0)
-	{
-		doFilter(1, 1);
-		return;
-	}
-
-	if (strcmp(Name, "showLPF_B") == 0)
-	{
-		doFilter(1, 2);
-		return;
-	}
-
-	if (strcmp(Name, "Low_A") == 0)
-	{
-		handleButton(0, 1);
-		return;
-	}
-
-	if (strcmp(Name, "High_A") == 0)
-	{
-		handleButton(0, 2);
-		return;
-	}
-
-	if (strcmp(Name, "Both_A") == 0)
-	{
-		handleButton(0, 3);
-		return;
-	}
-
-	if (strcmp(Name, "Stop_A") == 0)
-	{
-		handleButton(0, 0);
-		return;
-	}
-
-
-	if (strcmp(Name, "Low_B") == 0)
-	{
-		handleButton(1, 1);
-		return;
-	}
-
-	if (strcmp(Name, "High_B") == 0)
-	{
-		handleButton(1, 2);
-		return;
-	}
-
-	if (strcmp(Name, "Both_B") == 0)
-	{
-		handleButton(1, 3);
-		return;
-	}
-
-	if (strcmp(Name, "Stop_B") == 0)
-	{
-		handleButton(1, 0);
-		return;
-	}
-
-	if (strcmp(Name, "Low_C") == 0)
-	{
-		handleButton(2, 1);
-		return;
-	}
-
-	if (strcmp(Name, "High_C") == 0)
-	{
-		handleButton(2, 2);
-		return;
-	}
-
-	if (strcmp(Name, "Both_C") == 0)
-	{
-		handleButton(2, 3);
-		return;
-	}
-
-	if (strcmp(Name, "Stop_C") == 0)
-	{
-		handleButton(2, 0);
-		return;
-	}
-
-	if (strcmp(Name, "Low_D") == 0)
-	{
-		handleButton(3, 1);
-		return;
-	}
-
-	if (strcmp(Name, "High_D") == 0)
-	{
-		handleButton(3, 2);
-		return;
-	}
-
-	if (strcmp(Name, "Both_D") == 0)
-	{
-		handleButton(3, 3);
-		return;
-	}
-
-	if (strcmp(Name, "Stop_D") == 0)
-	{
-		handleButton(3, 0);
-		return;
-	}
-
-	QMessageBox msgBox;
-	msgBox.setWindowTitle("MessageBox Title");
-	msgBox.setText("You Clicked " + ((QPushButton*)sender())->objectName());
-	msgBox.exec();
-}
-
-Ui_ModemDialog * Dlg;
-
-QDialog * modemUI;
-QDialog * deviceUI;
-
-void QtSoundModem::doModems()
-{
-	Dlg = new(Ui_ModemDialog);
-
-	QDialog UI;
-	char valChar[10];
-
-	Dlg->setupUi(&UI);
-
-	modemUI = &UI;
-	deviceUI = 0;
-
-	myResize *resize = new myResize();
-
-	UI.installEventFilter(resize);
-
-	sprintf(valChar, "%d", bpf[0]);
-	Dlg->BPFWidthA->setText(valChar);
-	sprintf(valChar, "%d", bpf[1]);
-	Dlg->BPFWidthB->setText(valChar);
-	sprintf(valChar, "%d", bpf[2]);
-	Dlg->BPFWidthC->setText(valChar);
-	sprintf(valChar, "%d", bpf[3]);
-	Dlg->BPFWidthD->setText(valChar);
-
-	sprintf(valChar, "%d", txbpf[0]);
-	Dlg->TXBPFWidthA->setText(valChar);
-	sprintf(valChar, "%d", txbpf[1]);
-	Dlg->TXBPFWidthB->setText(valChar);
-	sprintf(valChar, "%d", txbpf[2]);
-	Dlg->TXBPFWidthC->setText(valChar);
-	sprintf(valChar, "%d", txbpf[3]);
-	Dlg->TXBPFWidthD->setText(valChar);
-
-	sprintf(valChar, "%d", lpf[0]);
-	Dlg->LPFWidthA->setText(valChar);
-	sprintf(valChar, "%d", lpf[1]);
-	Dlg->LPFWidthB->setText(valChar);
-	sprintf(valChar, "%d", lpf[2]);
-	Dlg->LPFWidthC->setText(valChar);
-	sprintf(valChar, "%d", lpf[4]);
-	Dlg->LPFWidthD->setText(valChar);
-
-	sprintf(valChar, "%d", BPF_tap[0]);
-	Dlg->BPFTapsA->setText(valChar);
-	sprintf(valChar, "%d", BPF_tap[1]);
-	Dlg->BPFTapsB->setText(valChar);
-	sprintf(valChar, "%d", BPF_tap[2]);
-	Dlg->BPFTapsC->setText(valChar);
-	sprintf(valChar, "%d", BPF_tap[3]);
-	Dlg->BPFTapsD->setText(valChar);
-
-	sprintf(valChar, "%d", LPF_tap[0]);
-	Dlg->LPFTapsA->setText(valChar);
-	sprintf(valChar, "%d", LPF_tap[1]);
-	Dlg->LPFTapsB->setText(valChar);
-	sprintf(valChar, "%d", LPF_tap[2]);
-	Dlg->LPFTapsC->setText(valChar);
-	sprintf(valChar, "%d", LPF_tap[3]);
-	Dlg->LPFTapsD->setText(valChar);
-
-	Dlg->preEmphAllA->setChecked(emph_all[0]);
-
-	if (emph_all[0])
-		Dlg->preEmphA->setDisabled(TRUE);
-	else
-		Dlg->preEmphA->setCurrentIndex(emph_db[0]);
-
-	Dlg->preEmphAllB->setChecked(emph_all[1]);
-
-	if (emph_all[1])
-		Dlg->preEmphB->setDisabled(TRUE);
-	else
-		Dlg->preEmphB->setCurrentIndex(emph_db[1]);
-
-	Dlg->preEmphAllC->setChecked(emph_all[2]);
-
-	if (emph_all[2])
-		Dlg->preEmphC->setDisabled(TRUE);
-	else
-		Dlg->preEmphC->setCurrentIndex(emph_db[2]);
-
-	Dlg->preEmphAllD->setChecked(emph_all[3]);
-
-	if (emph_all[3])
-		Dlg->preEmphD->setDisabled(TRUE);
-	else
-		Dlg->preEmphD->setCurrentIndex(emph_db[3]);
-
-
-	Dlg->nonAX25A->setChecked(NonAX25[0]);
-	Dlg->nonAX25B->setChecked(NonAX25[1]);
-	Dlg->nonAX25C->setChecked(NonAX25[2]);
-	Dlg->nonAX25D->setChecked(NonAX25[3]);
-
-	Dlg->KISSOptA->setChecked(KISS_opt[0]);
-	Dlg->KISSOptB->setChecked(KISS_opt[1]);
-	Dlg->KISSOptC->setChecked(KISS_opt[2]);
-	Dlg->KISSOptD->setChecked(KISS_opt[3]);
-
-	sprintf(valChar, "%d", txdelay[0]);
-	Dlg->TXDelayA->setText(valChar);
-	sprintf(valChar, "%d", txdelay[1]);
-	Dlg->TXDelayB->setText(valChar);
-	sprintf(valChar, "%d", txdelay[2]);
-	Dlg->TXDelayC->setText(valChar);
-	sprintf(valChar, "%d", txdelay[3]);
-	Dlg->TXDelayD->setText(valChar);
-
-	sprintf(valChar, "%d", txtail[0]);
-	Dlg->TXTailA->setText(valChar);
-	sprintf(valChar, "%d", txtail[1]);
-	Dlg->TXTailB->setText(valChar);
-	sprintf(valChar, "%d", txtail[2]);
-	Dlg->TXTailC->setText(valChar);
-	sprintf(valChar, "%d", txtail[3]);
-	Dlg->TXTailD->setText(valChar);
-
-	Dlg->FrackA->setText(QString::number(frack_time[0]));
-	Dlg->FrackB->setText(QString::number(frack_time[1]));
-	Dlg->FrackC->setText(QString::number(frack_time[2]));
-	Dlg->FrackD->setText(QString::number(frack_time[3]));
-
-	Dlg->RetriesA->setText(QString::number(fracks[0]));
-	Dlg->RetriesB->setText(QString::number(fracks[1]));
-	Dlg->RetriesC->setText(QString::number(fracks[2]));
-	Dlg->RetriesD->setText(QString::number(fracks[3]));
-
-	sprintf(valChar, "%d", RCVR[0]);
-	Dlg->AddRXA->setText(valChar);
-	sprintf(valChar, "%d", RCVR[1]);
-	Dlg->AddRXB->setText(valChar);
-	sprintf(valChar, "%d", RCVR[2]);
-	Dlg->AddRXC->setText(valChar);
-	sprintf(valChar, "%d", RCVR[3]);
-	Dlg->AddRXD->setText(valChar);
-
-	sprintf(valChar, "%d", rcvr_offset[0]);
-	Dlg->RXShiftA->setText(valChar);
-
-	sprintf(valChar, "%d", rcvr_offset[1]);
-	Dlg->RXShiftB->setText(valChar);
-
-	sprintf(valChar, "%d", rcvr_offset[2]);
-	Dlg->RXShiftC->setText(valChar);
-	sprintf(valChar, "%d", rcvr_offset[3]);
-	Dlg->RXShiftD->setText(valChar);
-
-	//	speed[1]
-	//	speed[2];
-
-	Dlg->recoverBitA->setCurrentIndex(recovery[0]);
-	Dlg->recoverBitB->setCurrentIndex(recovery[1]);
-	Dlg->recoverBitC->setCurrentIndex(recovery[2]);
-	Dlg->recoverBitD->setCurrentIndex(recovery[3]);
-
-	Dlg->fx25ModeA->setCurrentIndex(fx25_mode[0]);
-	Dlg->fx25ModeB->setCurrentIndex(fx25_mode[1]);
-	Dlg->fx25ModeC->setCurrentIndex(fx25_mode[2]);
-	Dlg->fx25ModeD->setCurrentIndex(fx25_mode[3]);
-
-	Dlg->IL2PModeA->setCurrentIndex(il2p_mode[0]);
-	Dlg->IL2PModeB->setCurrentIndex(il2p_mode[1]);
-	Dlg->IL2PModeC->setCurrentIndex(il2p_mode[2]);
-	Dlg->IL2PModeD->setCurrentIndex(il2p_mode[3]);
-
-	Dlg->CWIDCall->setText(CWIDCall);
-	Dlg->CWIDInterval->setText(QString::number(CWIDInterval));
-
-	if (CWIDType)
-		Dlg->radioButton_2->setChecked(1);
-	else
-		Dlg->CWIDType->setChecked(1);
-
-	Dlg->RSIDSABM_A->setChecked(RSID_SABM[0]);
-	Dlg->RSIDSABM_B->setChecked(RSID_SABM[1]);
-	Dlg->RSIDSABM_C->setChecked(RSID_SABM[2]);
-	Dlg->RSIDSABM_D->setChecked(RSID_SABM[3]);
-
-	Dlg->RSIDUI_A->setChecked(RSID_UI[0]);
-	Dlg->RSIDUI_B->setChecked(RSID_UI[1]);
-	Dlg->RSIDUI_C->setChecked(RSID_UI[2]);
-	Dlg->RSIDUI_D->setChecked(RSID_UI[3]);
-
-	Dlg->DigiCallsA->setText(MyDigiCall[0]);
-	Dlg->DigiCallsB->setText(MyDigiCall[1]);
-	Dlg->DigiCallsC->setText(MyDigiCall[2]);
-	Dlg->DigiCallsD->setText(MyDigiCall[3]);
-
-	Dlg->RSID_1_SETMODEM->setChecked(RSID_SetModem[0]);
-	Dlg->RSID_2_SETMODEM->setChecked(RSID_SetModem[1]);
-	Dlg->RSID_3_SETMODEM->setChecked(RSID_SetModem[2]);
-	Dlg->RSID_4_SETMODEM->setChecked(RSID_SetModem[3]);
-	
-	connect(Dlg->showBPF_A, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showTXBPF_A, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showLPF_A, SIGNAL(released()), this, SLOT(clickedSlot()));
-
-	connect(Dlg->showBPF_B, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showTXBPF_B, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showLPF_B, SIGNAL(released()), this, SLOT(clickedSlot()));
-
-	connect(Dlg->showBPF_C, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showTXBPF_C, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showLPF_C, SIGNAL(released()), this, SLOT(clickedSlot()));
-
-	connect(Dlg->showBPF_D, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showTXBPF_D, SIGNAL(released()), this, SLOT(clickedSlot()));
-	connect(Dlg->showLPF_D, SIGNAL(released()), this, SLOT(clickedSlot()));
-
-	connect(Dlg->okButton, SIGNAL(clicked()), this, SLOT(modemaccept()));
-	connect(Dlg->modemSave, SIGNAL(clicked()), this, SLOT(modemSave()));
-	connect(Dlg->cancelButton, SIGNAL(clicked()), this, SLOT(modemreject()));
-
-	connect(Dlg->SendRSID_1, SIGNAL(clicked()), this, SLOT(doRSIDA()));
-	connect(Dlg->SendRSID_2, SIGNAL(clicked()), this, SLOT(doRSIDB()));
-	connect(Dlg->SendRSID_3, SIGNAL(clicked()), this, SLOT(doRSIDC()));
-	connect(Dlg->SendRSID_4, SIGNAL(clicked()), this, SLOT(doRSIDD()));
-
-	connect(Dlg->preEmphAllA, SIGNAL(stateChanged(int)), this, SLOT(preEmphAllAChanged(int)));
-	connect(Dlg->preEmphAllB, SIGNAL(stateChanged(int)), this, SLOT(preEmphAllBChanged(int)));
-	connect(Dlg->preEmphAllC, SIGNAL(stateChanged(int)), this, SLOT(preEmphAllCChanged(int)));
-	connect(Dlg->preEmphAllD, SIGNAL(stateChanged(int)), this, SLOT(preEmphAllDChanged(int)));
-
-	UI.exec();
-}
-
-void QtSoundModem::preEmphAllAChanged(int state)
-{
-	Dlg->preEmphA->setDisabled(state);
-}
-
-void QtSoundModem::preEmphAllBChanged(int state)
-{
-	Dlg->preEmphB->setDisabled(state);
-}
-
-void QtSoundModem::preEmphAllCChanged(int state)
-{
-	Dlg->preEmphC->setDisabled(state);
-}
-
-void QtSoundModem::preEmphAllDChanged(int state)
-{
-	Dlg->preEmphD->setDisabled(state);
-}
-
-extern "C" void get_exclude_list(char * line, TStringList * list);
-
-void QtSoundModem::modemaccept()
-{
-	modemSave();
-	delete(Dlg);
-	saveSettings();
-
-	modemUI->accept();
-
-}
-
-void QtSoundModem::modemSave()
-{
-	QVariant Q;
-	
-	emph_all[0] = Dlg->preEmphAllA->isChecked();
-	emph_db[0] = Dlg->preEmphA->currentIndex();
-
-	emph_all[1] = Dlg->preEmphAllB->isChecked();
-	emph_db[1] = Dlg->preEmphB->currentIndex();
-
-	emph_all[2] = Dlg->preEmphAllC->isChecked();
-	emph_db[2] = Dlg->preEmphC->currentIndex();
-
-	emph_all[3] = Dlg->preEmphAllD->isChecked();
-	emph_db[3] = Dlg->preEmphD->currentIndex();
-
-	NonAX25[0] = Dlg->nonAX25A->isChecked();
-	NonAX25[1] = Dlg->nonAX25B->isChecked();
-	NonAX25[2] = Dlg->nonAX25C->isChecked();
-	NonAX25[3] = Dlg->nonAX25D->isChecked();
-
-	KISS_opt[0] = Dlg->KISSOptA->isChecked();
-	KISS_opt[1] = Dlg->KISSOptB->isChecked();
-	KISS_opt[2] = Dlg->KISSOptC->isChecked();
-	KISS_opt[3] = Dlg->KISSOptD->isChecked();
-
-	if (emph_db[0] < 0 || emph_db[0] > nr_emph)
-		emph_db[0] = 0;
-
-	if (emph_db[1] < 0 || emph_db[1] > nr_emph)
-		emph_db[1] = 0;
-
-	if (emph_db[2] < 0 || emph_db[2] > nr_emph)
-		emph_db[2] = 0;
-
-	if (emph_db[3] < 0 || emph_db[3] > nr_emph)
-		emph_db[3] = 0;
-
-	Q = Dlg->TXDelayA->text();
-	txdelay[0] = Q.toInt();
-
-	Q = Dlg->TXDelayB->text();
-	txdelay[1] = Q.toInt();
-	
-	Q = Dlg->TXDelayC->text();
-	txdelay[2] = Q.toInt();
-
-	Q = Dlg->TXDelayD->text();
-	txdelay[3] = Q.toInt();
-
-	Q = Dlg->TXTailA->text();
-	txtail[0] = Q.toInt();
-
-	Q = Dlg->TXTailB->text();
-	txtail[1] = Q.toInt();
-
-	Q = Dlg->TXTailC->text();
-	txtail[2] = Q.toInt();
-
-	txtail[3] = Dlg->TXTailD->text().toInt();
-
-	frack_time[0] = Dlg->FrackA->text().toInt();
-	frack_time[1] = Dlg->FrackB->text().toInt();
-	frack_time[2] = Dlg->FrackC->text().toInt();
-	frack_time[3] = Dlg->FrackD->text().toInt();
-
-	fracks[0] = Dlg->RetriesA->text().toInt();
-	fracks[1] = Dlg->RetriesB->text().toInt();
-	fracks[2] = Dlg->RetriesC->text().toInt();
-	fracks[3] = Dlg->RetriesD->text().toInt();
-
-	Q = Dlg->AddRXA->text();
-	RCVR[0] = Q.toInt();
-
-	Q = Dlg->AddRXB->text();
-	RCVR[1] = Q.toInt();
-
-	Q = Dlg->AddRXC->text();
-	RCVR[2] = Q.toInt();
-
-	Q = Dlg->AddRXD->text();
-	RCVR[3] = Q.toInt();
-
-	Q = Dlg->RXShiftA->text();
-	rcvr_offset[0] = Q.toInt();
-
-	Q = Dlg->RXShiftB->text();
-	rcvr_offset[1] = Q.toInt();
-
-	Q = Dlg->RXShiftC->text();
-	rcvr_offset[2] = Q.toInt();
-
-	Q = Dlg->RXShiftD->text();
-	rcvr_offset[3] = Q.toInt();
-
-	fx25_mode[0] = Dlg->fx25ModeA->currentIndex();
-	fx25_mode[1] = Dlg->fx25ModeB->currentIndex();
-	fx25_mode[2] = Dlg->fx25ModeC->currentIndex();
-	fx25_mode[3] = Dlg->fx25ModeD->currentIndex();
-
-	il2p_mode[0] = Dlg->IL2PModeA->currentIndex();
-	il2p_mode[1] = Dlg->IL2PModeB->currentIndex();
-	il2p_mode[2] = Dlg->IL2PModeC->currentIndex();
-	il2p_mode[3] = Dlg->IL2PModeD->currentIndex();
-
-	recovery[0] = Dlg->recoverBitA->currentIndex();
-	recovery[1] = Dlg->recoverBitB->currentIndex();
-	recovery[2] = Dlg->recoverBitC->currentIndex();
-	recovery[3] = Dlg->recoverBitD->currentIndex();
-
-
-	strcpy(CWIDCall, Dlg->CWIDCall->text().toUtf8().toUpper());
-	CWIDInterval = Dlg->CWIDInterval->text().toInt();
-	CWIDType = Dlg->radioButton_2->isChecked();
-
-	if (CWIDInterval)
-		cwidtimer->start(CWIDInterval * 60000);
-	else
-		cwidtimer->stop();
-
-
-	RSID_SABM[0] = Dlg->RSIDSABM_A->isChecked();
-	RSID_SABM[1] = Dlg->RSIDSABM_B->isChecked();
-	RSID_SABM[2] = Dlg->RSIDSABM_C->isChecked();
-	RSID_SABM[3] = Dlg->RSIDSABM_D->isChecked();
-
-	RSID_UI[0] = Dlg->RSIDUI_A->isChecked();
-	RSID_UI[1] = Dlg->RSIDUI_B->isChecked();
-	RSID_UI[2] = Dlg->RSIDUI_C->isChecked();
-	RSID_UI[3] = Dlg->RSIDUI_D->isChecked();
-
-	RSID_SetModem[0] = Dlg->RSID_1_SETMODEM->isChecked();
-	RSID_SetModem[1] = Dlg->RSID_2_SETMODEM->isChecked();
-	RSID_SetModem[2] = Dlg->RSID_3_SETMODEM->isChecked();
-	RSID_SetModem[3] = Dlg->RSID_4_SETMODEM->isChecked();
-
-	Q = Dlg->DigiCallsA->text();
-	strcpy(MyDigiCall[0], Q.toString().toUtf8().toUpper());
-
-	Q = Dlg->DigiCallsB->text();
-	strcpy(MyDigiCall[1], Q.toString().toUtf8().toUpper());
-
-	Q = Dlg->DigiCallsC->text();
-	strcpy(MyDigiCall[2], Q.toString().toUtf8().toUpper());
-
-	Q = Dlg->DigiCallsD->text();
-	strcpy(MyDigiCall[3], Q.toString().toUtf8().toUpper());
-
-	int i;
-
-	for (i = 0; i < 4; i++)
-	{
-		initTStringList(&list_digi_callsigns[i]);
-
-		get_exclude_list(MyDigiCall[i], &list_digi_callsigns[i]);
-	}
-
-}
-
-void QtSoundModem::modemreject()
-{
-	delete(Dlg);
-	modemUI->reject();
-}
-
-void QtSoundModem::doRSIDA()
-{
-	needRSID[0] = 1;
-}
-
-void QtSoundModem::doRSIDB()
-{
-	needRSID[1] = 1;
-}
-
-void QtSoundModem::doRSIDC()
-{
-	needRSID[2] = 1;
-}
-
-void QtSoundModem::doRSIDD()
-{
-	needRSID[3] = 1;
-}
-
-
-
-
-void QtSoundModem::doFilter(int Chan, int Filter)
-{
-	Ui_Dialog Dev;
-	QImage * bitmap;
-
-	QDialog UI;
-
-	Dev.setupUi(&UI);
-
-	bitmap = new QImage(642, 312, QImage::Format_RGB32);
-
-	bitmap->fill(qRgb(255, 255, 255));
-
-	QPainter qPainter(bitmap);
-	qPainter.setBrush(Qt::NoBrush);
-	qPainter.setPen(Qt::black);
-
-	if (Filter == 0)
-		make_graph_buf(DET[0][0].BPF_core[Chan], BPF_tap[Chan], &qPainter);
-	else if (Filter == 1)
-		make_graph_buf(tx_BPF_core[Chan], tx_BPF_tap[Chan], &qPainter);
-	else
-		make_graph_buf(LPF_core[Chan], LPF_tap[Chan], &qPainter);
-
-	qPainter.end();
-	Dev.label->setPixmap(QPixmap::fromImage(*bitmap));
-
-	UI.exec();
-
-}
-
-Ui_devicesDialog * Dev;
-
-char NewPTTPort[80];
-
-int newSoundMode = 0;
-int oldSoundMode = 0;
-
-void QtSoundModem::SoundModeChanged(bool State)
-{
-	UNUSED(State);
-
-	// Mustn't change SoundMode until dialog is accepted
-
-	if (Dev->UDP->isChecked())
-		newSoundMode = 3;
-	else if (Dev->PULSE->isChecked())
-		newSoundMode = 2;
-	else
-		newSoundMode = Dev->OSS->isChecked();
-
-}
-
-void QtSoundModem::DualPTTChanged(bool State)
-{
-	UNUSED(State);
-
-	// Forse Evaluation of Cat Port setting
-
-	PTTPortChanged(0);
-}
-
-void QtSoundModem::CATChanged(bool State)
-{
-	UNUSED(State);
-	PTTPortChanged(0);
-}
-
-void QtSoundModem::PTTPortChanged(int Selected)
-{
-	UNUSED(Selected);
-
-	QVariant Q = Dev->PTTPort->currentText();
-	strcpy(NewPTTPort, Q.toString().toUtf8());
-
-	Dev->RTSDTR->setVisible(false);
-	Dev->CAT->setVisible(false);
-
-	Dev->PTTOnLab->setVisible(false);
-	Dev->PTTOn->setVisible(false);
-	Dev->PTTOff->setVisible(false);
-	Dev->PTTOffLab->setVisible(false);
-	Dev->CATLabel->setVisible(false);
-	Dev->CATSpeed->setVisible(false);
-
-	Dev->GPIOLab->setVisible(false);
-	Dev->GPIOLeft->setVisible(false);
-	Dev->GPIORight->setVisible(false);
-	Dev->GPIOLab2->setVisible(false);
-
-	Dev->CM108Label->setVisible(false);
-	Dev->VIDPID->setVisible(false);
-
-	if (strcmp(NewPTTPort, "None") == 0)
-	{
-	}
-	else if (strcmp(NewPTTPort, "GPIO") == 0)
-	{
-		Dev->GPIOLab->setVisible(true);
-		Dev->GPIOLeft->setVisible(true);
-		if (Dev->DualPTT->isChecked())
-		{
-			Dev->GPIORight->setVisible(true);
-			Dev->GPIOLab2->setVisible(true);
-		}
-	}
-
-	else if (strcmp(NewPTTPort, "CM108") == 0)
-	{
-		Dev->CM108Label->setVisible(true);
-//#ifdef __ARM_ARCHX
-		Dev->CM108Label->setText("CM108 Device");
-//#else
-//		Dev->CM108Label->setText("CM108 VID/PID");
-//#endif
-		Dev->VIDPID->setText(CM108Addr);
-		Dev->VIDPID->setVisible(true);
-	}
-	else if (strcmp(NewPTTPort, "HAMLIB") == 0)
-	{
-		Dev->CM108Label->setVisible(true);
-		Dev->CM108Label->setText("rigctrld Port");
-		Dev->VIDPID->setText(QString::number(HamLibPort));
-		Dev->VIDPID->setVisible(true);
-		Dev->PTTOnLab->setText("rigctrld Host");
-		Dev->PTTOnLab->setVisible(true);
-		Dev->PTTOn->setText(HamLibHost);
-		Dev->PTTOn->setVisible(true);
-	}
-	else
-	{
-		Dev->RTSDTR->setVisible(true);
-		Dev->CAT->setVisible(true);
-
-		if (Dev->CAT->isChecked())
-		{
-			Dev->PTTOnLab->setVisible(true);
-			Dev->PTTOnLab->setText("PTT On String");
-			Dev->PTTOn->setText(PTTOnString);
-			Dev->PTTOn->setVisible(true);
-			Dev->PTTOff->setVisible(true);
-			Dev->PTTOff->setText(PTTOffString);
-			Dev->PTTOffLab->setVisible(true);
-			Dev->CATLabel->setVisible(true);
-			Dev->CATSpeed->setVisible(true);
-		}
-	}
-}
-
-bool myResize::eventFilter(QObject *obj, QEvent *event)
-{
-	if (event->type() == QEvent::Resize)
-	{
-		QResizeEvent *resizeEvent = static_cast<QResizeEvent *>(event);
-		QSize size = resizeEvent->size();
-		int h = size.height();
-		int w = size.width();
-
-		if (obj == deviceUI)
-			Dev->scrollArea->setGeometry(QRect(5, 5, w - 10, h - 10));
-		else
-			Dlg->scrollArea->setGeometry(QRect(5, 5, w - 10, h - 10));
-
-		return true;
-	}
-	return QObject::eventFilter(obj, event);
-}
-
-void QtSoundModem::doDevices()
-{
-	char valChar[10];
-
-	Dev = new(Ui_devicesDialog);
-
-	QDialog UI;
-
-	int i;
-
-	Dev->setupUi(&UI);
-
-	deviceUI = &UI;
-	modemUI = 0;
-
-	myResize *resize = new myResize();
-
-	UI.installEventFilter(resize);
-
-	newSoundMode = SoundMode;
-	oldSoundMode = SoundMode;
-
-#ifdef WIN32
-	Dev->ALSA->setText("WaveOut");
-	Dev->OSS->setVisible(0);
-	Dev->PULSE->setVisible(0);
-#endif
-
-	if (SoundMode == 0)
-		Dev->ALSA->setChecked(1);
-	else if (SoundMode == 1)
-		Dev->OSS->setChecked(1);
-	else if (SoundMode == 2)
-		Dev->PULSE->setChecked(1);
-	else if (SoundMode == 2)
-		Dev->UDP->setChecked(1);
-
-	connect(Dev->ALSA, SIGNAL(toggled(bool)), this, SLOT(SoundModeChanged(bool)));
-	connect(Dev->OSS, SIGNAL(toggled(bool)), this, SLOT(SoundModeChanged(bool)));
-	connect(Dev->PULSE, SIGNAL(toggled(bool)), this, SLOT(SoundModeChanged(bool)));
-	connect(Dev->UDP, SIGNAL(toggled(bool)), this, SLOT(SoundModeChanged(bool)));
-
-	for (i = 0; i < PlaybackCount; i++)
-		Dev->outputDevice->addItem(&PlaybackNames[i][0]);
-
-	i = Dev->outputDevice->findText(PlaybackDevice, Qt::MatchContains);
-
-
-	if (i == -1)
-	{
-		// Add device to list
-
-		Dev->outputDevice->addItem(PlaybackDevice);
-		i = Dev->outputDevice->findText(PlaybackDevice, Qt::MatchContains);
-	}
-
-	Dev->outputDevice->setCurrentIndex(i);
-
-	for (i = 0; i < CaptureCount; i++)
-		Dev->inputDevice->addItem(&CaptureNames[i][0]);
-
-	i = Dev->inputDevice->findText(CaptureDevice, Qt::MatchContains);
-
-	if (i == -1)
-	{
-		// Add device to list
-
-		Dev->inputDevice->addItem(CaptureDevice);
-		i = Dev->inputDevice->findText(CaptureDevice, Qt::MatchContains);
-	}
-	Dev->inputDevice->setCurrentIndex(i);
-
-	Dev->Modem_1_Chan->setCurrentIndex(soundChannel[0]);
-	Dev->Modem_2_Chan->setCurrentIndex(soundChannel[1]);
-	Dev->Modem_3_Chan->setCurrentIndex(soundChannel[2]);
-	Dev->Modem_4_Chan->setCurrentIndex(soundChannel[3]);
-
-	// Disable "None" option in first modem
-
-	QStandardItemModel *model = dynamic_cast<QStandardItemModel *>(Dev->Modem_1_Chan->model());
-	QStandardItem * item = model->item(0, 0);
-	item->setEnabled(false);
-
-	Dev->singleChannelOutput->setChecked(SCO);
-	Dev->colourWaterfall->setChecked(raduga);
-
-	sprintf(valChar, "%d", KISSPort);
-	Dev->KISSPort->setText(valChar);
-	Dev->KISSEnabled->setChecked(KISSServ);
-
-	sprintf(valChar, "%d", AGWPort);
-	Dev->AGWPort->setText(valChar);
-	Dev->AGWEnabled->setChecked(AGWServ);
-
-	Dev->PTTOn->setText(PTTOnString);
-	Dev->PTTOff->setText(PTTOffString);
-
-	sprintf(valChar, "%d", PTTBAUD);
-	Dev->CATSpeed->setText(valChar);
-
-	sprintf(valChar, "%d", UDPClientPort);
-	Dev->UDPPort->setText(valChar);
-	Dev->UDPTXHost->setText(UDPHost);
-
-	if (UDPServerPort != TXPort)
-		sprintf(valChar, "%d/%d", UDPServerPort, TXPort);
-	else
-		sprintf(valChar, "%d", UDPServerPort);
-
-	Dev->UDPTXPort->setText(valChar);
-
-	Dev->UDPEnabled->setChecked(UDPServ);
-
-	sprintf(valChar, "%d", pttGPIOPin);
-	Dev->GPIOLeft->setText(valChar);
-	sprintf(valChar, "%d", pttGPIOPinR);
-	Dev->GPIORight->setText(valChar);
-
-	Dev->VIDPID->setText(CM108Addr);
-
-	QStringList items;
-
-	connect(Dev->CAT, SIGNAL(toggled(bool)), this, SLOT(CATChanged(bool)));
-	connect(Dev->DualPTT, SIGNAL(toggled(bool)), this, SLOT(DualPTTChanged(bool)));
-	connect(Dev->PTTPort, SIGNAL(currentIndexChanged(int)), this, SLOT(PTTPortChanged(int)));
-
-
-
-	if (PTTMode == PTTCAT)
-		Dev->CAT->setChecked(true);
-	else
-		Dev->RTSDTR->setChecked(true);
-
-	for (const QSerialPortInfo &info : Ports)
-	{
-		items.append(info.portName());
-	}
-
-	items.sort();
-
-	Dev->PTTPort->addItem("None");
-	Dev->PTTPort->addItem("CM108");
-
-	//#ifdef __ARM_ARCH
-
-	Dev->PTTPort->addItem("GPIO");
-
-	//#endif
-
-	Dev->PTTPort->addItem("HAMLIB");
-
-	for (const QString &info : items)
-	{
-		Dev->PTTPort->addItem(info);
-	}
-
-	Dev->PTTPort->setCurrentIndex(Dev->PTTPort->findText(PTTPort, Qt::MatchFixedString));
-
-	PTTPortChanged(0);				// Force reevaluation
-
-	Dev->txRotation->setChecked(TX_rotate);
-	Dev->DualPTT->setChecked(DualPTT);
-
-	Dev->multiCore->setChecked(multiCore);
-
-	QObject::connect(Dev->okButton, SIGNAL(clicked()), this, SLOT(deviceaccept()));
-	QObject::connect(Dev->cancelButton, SIGNAL(clicked()), this, SLOT(devicereject()));
-
-	UI.exec();
-
-}
-
-void QtSoundModem::deviceaccept()
-{
-	QVariant Q = Dev->inputDevice->currentText();
-	int cardChanged = 0;
-	char portString[32];
-
-	if (Dev->UDP->isChecked())
-	{
-		// cant have server and slave
-
-		if (Dev->UDPEnabled->isChecked())
-		{
-			QMessageBox::about(this, tr("QtSoundModem"),
-				tr("Can't have UDP sound source and UDP server at same time"));
-			return;
-		}
-	}
-
-	if (oldSoundMode != newSoundMode)
-	{
-		QMessageBox msgBox;
-
-		msgBox.setText("QtSoundModem must restart to change Sound Mode.\n"
-			"Program will close if you hit Ok\n"
-			"You will need to reselect audio devices after restarting");
-
-		msgBox.setStandardButtons(QMessageBox::Ok | QMessageBox::Cancel);
-
-		int i = msgBox.exec();
-
-		if (i == QMessageBox::Ok)
-		{
-			SoundMode = newSoundMode;
-
-			saveSettings();
-
-			Closing = 1;
-			return;
-		}
-
-		if (oldSoundMode == 0)
-			Dev->ALSA->setChecked(1);
-		else if (oldSoundMode == 1)
-			Dev->OSS->setChecked(1);
-		else if (oldSoundMode == 2)
-			Dev->PULSE->setChecked(1);
-		else if (oldSoundMode == 3)
-			Dev->UDP->setChecked(1);
-
-		QMessageBox::about(this, tr("Info"),
-			tr("<p align = 'center'>Changes not saved</p>"));
-
-		return;
-
-	}
-
-	if (strcmp(CaptureDevice, Q.toString().toUtf8()) != 0)
-	{
-		strcpy(CaptureDevice, Q.toString().toUtf8());
-		cardChanged = 1;
-	}
-
-	CaptureIndex = Dev->inputDevice->currentIndex();
-
-	Q = Dev->outputDevice->currentText();
-
-	if (strcmp(PlaybackDevice, Q.toString().toUtf8()) != 0)
-	{
-		strcpy(PlaybackDevice, Q.toString().toUtf8());
-		cardChanged = 1;
-	}
-
-	PlayBackIndex = Dev->outputDevice->currentIndex();
-
-	soundChannel[0] = Dev->Modem_1_Chan->currentIndex();
-	soundChannel[1] = Dev->Modem_2_Chan->currentIndex();
-	soundChannel[2] = Dev->Modem_3_Chan->currentIndex();
-	soundChannel[3] = Dev->Modem_4_Chan->currentIndex();
-
-	UsingLeft = 0;
-	UsingRight = 0;
-	UsingBothChannels = 0;
-
-	for (int i = 0; i < 4; i++)
-	{
-		if (soundChannel[i] == LEFT)
-		{
-			UsingLeft = 1;
-			modemtoSoundLR[i] = 0;
-		}
-		else if (soundChannel[i] == RIGHT)
-		{
-			UsingRight = 1;
-			modemtoSoundLR[i] = 1;
-		}
-	}
-
-	if (UsingLeft && UsingRight)
-		UsingBothChannels = 1;
-
-
-	SCO = Dev->singleChannelOutput->isChecked();
-	raduga = Dev->colourWaterfall->isChecked();
-	AGWServ = Dev->AGWEnabled->isChecked();
-	KISSServ = Dev->KISSEnabled->isChecked();
-
-	Q = Dev->KISSPort->text();
-	KISSPort = Q.toInt();
-
-	Q = Dev->AGWPort->text();
-	AGWPort = Q.toInt();
-
-	Q = Dev->PTTPort->currentText();
-	strcpy(PTTPort, Q.toString().toUtf8());
-
-	DualPTT = Dev->DualPTT->isChecked();
-	TX_rotate = Dev->txRotation->isChecked();
-	multiCore = Dev->multiCore->isChecked();
-
-	if (Dev->CAT->isChecked())
-		PTTMode = PTTCAT;
-	else
-		PTTMode = PTTRTS;
-
-	Q = Dev->PTTOn->text();
-	strcpy(PTTOnString, Q.toString().toUtf8());
-	Q = Dev->PTTOff->text();
-	strcpy(PTTOffString, Q.toString().toUtf8());
-
-	Q = Dev->CATSpeed->text();
-	PTTBAUD = Q.toInt();
-
-	Q = Dev->UDPPort->text();
-	UDPClientPort = Q.toInt();
-
-
-	Q = Dev->UDPTXPort->text();
-	strcpy(portString, Q.toString().toUtf8());
-	UDPServerPort = atoi(portString);
-
-	if (strchr(portString, '/'))
-	{
-		char * ptr = strlop(portString, '/');
-		TXPort = atoi(ptr);
-	}
-	else
-		TXPort = UDPServerPort;
-
-	Q = Dev->UDPTXHost->text();
-	strcpy(UDPHost, Q.toString().toUtf8());
-
-	UDPServ = Dev->UDPEnabled->isChecked();
-
-	Q = Dev->GPIOLeft->text();
-	pttGPIOPin = Q.toInt();
-
-	Q = Dev->GPIORight->text();
-	pttGPIOPinR = Q.toInt();
-
-	Q = Dev->VIDPID->text();
-
-	if (strcmp(PTTPort, "CM108") == 0)
-		strcpy(CM108Addr, Q.toString().toUtf8());
-	else if (strcmp(PTTPort, "HAMLIB") == 0)
-	{
-		HamLibPort = Q.toInt();
-		Q = Dev->PTTOn->text();
-		strcpy(HamLibHost, Q.toString().toUtf8());
-	}
-
-	ClosePTTPort();
-	OpenPTTPort();
-
-	wf_pointer(soundChannel[0]);
-	wf_pointer(soundChannel[1]);
-
-	delete(Dev);
-	saveSettings();
-	deviceUI->accept();
-
-	if (cardChanged)
-	{
-		InitSound(1);
-	}
-
-	// Reset title and tooltip in case ports changed
-
-	char Title[128];
-	sprintf(Title, "QtSoundModem Version %s Ports %d/%d", VersionString, AGWPort, KISSPort);
-	w->setWindowTitle(Title);
-
-	sprintf(Title, "QtSoundModem %d %d", AGWPort, KISSPort);
-	if (trayIcon)
-		trayIcon->setToolTip(Title);
-
-	QSize newSize(this->size());
-	QSize oldSize(this->size());
-
-	QResizeEvent *myResizeEvent = new QResizeEvent(newSize, oldSize);
-
-	QCoreApplication::postEvent(this, myResizeEvent);  
-}
-
-void QtSoundModem::devicereject()
-{	
-	delete(Dev);
-	deviceUI->reject();
-}
-
-void QtSoundModem::handleButton(int Port, int Type)
-{
-	// interlock calib with CWID
-
-	if (calib_mode[0] == 4)		// CWID
-		return;
-	
-	doCalib(Port, Type);
-}
-
-void QtSoundModem::doRestartWF()
-{
-	if (Firstwaterfall)
-	{
-		initWaterfall(0, 0);
-		initWaterfall(0, 1);
-	}
-
-	if (Secondwaterfall)
-	{
-		initWaterfall(1, 0);
-		initWaterfall(1, 1);
-	}
-}
-
-
-void QtSoundModem::doAbout()
-{
-	QMessageBox::about(this, tr("About"),
-		tr("G8BPQ's port of UZ7HO's Soundmodem\n\nCopyright (C) 2019-2020 Andrei Kopanchuk UZ7HO"));
-}
-
-void QtSoundModem::doCalibrate()
-{
-	Ui_calDialog Calibrate;
-	{
-		QDialog UI;
-		Calibrate.setupUi(&UI);
-
-		connect(Calibrate.Low_A, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.High_A, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Both_A, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Stop_A, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Low_B, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.High_B, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Both_B, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Stop_B, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Low_C, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.High_C, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Both_C, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Stop_C, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Low_D, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.High_D, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Both_D, SIGNAL(released()), this, SLOT(clickedSlot()));
-		connect(Calibrate.Stop_D, SIGNAL(released()), this, SLOT(clickedSlot()));
-
-		/*
-		
-		connect(Calibrate.Low_A, &QPushButton::released, this, [=] { handleButton(0, 1); });
-		connect(Calibrate.High_A, &QPushButton::released, this, [=] { handleButton(0, 2); });
-		connect(Calibrate.Both_A, &QPushButton::released, this, [=] { handleButton(0, 3); });
-		connect(Calibrate.Stop_A, &QPushButton::released, this, [=] { handleButton(0, 0); });
-		connect(Calibrate.Low_B, &QPushButton::released, this, [=] { handleButton(1, 1); });
-		connect(Calibrate.High_B, &QPushButton::released, this, [=] { handleButton(1, 2); });
-		connect(Calibrate.Both_B, &QPushButton::released, this, [=] { handleButton(1, 3); });
-		connect(Calibrate.Stop_B, &QPushButton::released, this, [=] { handleButton(1, 0); });
-
-//		connect(Calibrate.High_A, SIGNAL(released()), this, SLOT(handleButton(1, 2)));
-*/
-		UI.exec();
-	}
-}
-
-void QtSoundModem::RefreshSpectrum(unsigned char * Data)
-{
-	int i;
-
-	// Last 4 bytes are level busy and Tuning lines
-
-	Waterfall[0]->fill(Black);
-
-	if (Data[206] != LastLevel)
-	{
-		LastLevel = Data[206];
-//		RefreshLevel(LastLevel);
-	}
-
-	if (Data[207] != LastBusy)
-	{
-		LastBusy = Data[207];
-//		Busy->setVisible(LastBusy);
-	}
-
-	for (i = 0; i < 205; i++)
-	{
-		int val = Data[0];
-
-		if (val > 63)
-			val = 63;
-
-		Waterfall[0]->setPixel(i, val, Yellow);
-		if (val < 62)
-			Waterfall[0]->setPixel(i, val + 1, Gold);
-		Data++;
-	}
-
-	ui.WaterfallA->setPixmap(QPixmap::fromImage(*Waterfall[0]));
-
-}
-
-void QtSoundModem::RefreshWaterfall(int snd_ch, unsigned char * Data)
-{
-	int j;
-	unsigned char * Line;
-	int len = Waterfall[0]->bytesPerLine();
-	int TopLine = NextWaterfallLine[snd_ch];
-
-	// Write line to cyclic buffer then draw starting with the line just written
-
-	// Length is 208 bytes, including Level and Busy flags
-
-	memcpy(&WaterfallLines[snd_ch][NextWaterfallLine[snd_ch]++][0], Data, 206);
-	if (NextWaterfallLine[snd_ch] > 63)
-		NextWaterfallLine[snd_ch] = 0;
-
-	for (j = 63; j > 0; j--)
-	{
-		Line = Waterfall[0]->scanLine(j);
-		memcpy(Line, &WaterfallLines[snd_ch][TopLine++][0], len);
-		if (TopLine > 63)
-			TopLine = 0;
-	}
-
-	ui.WaterfallA->setPixmap(QPixmap::fromImage(*Waterfall[0]));
-}
-
-
-void QtSoundModem::sendtoTrace(char * Msg, int tx)
-{
-	const QTextCursor old_cursor = monWindowCopy->textCursor();
-	const int old_scrollbar_value = monWindowCopy->verticalScrollBar()->value();
-	const bool is_scrolled_down = old_scrollbar_value == monWindowCopy->verticalScrollBar()->maximum();
-
-	// Move the cursor to the end of the document.
-	monWindowCopy->moveCursor(QTextCursor::End);
-
-	// Insert the text at the position of the cursor (which is the end of the document).
-
-	if (tx)
-		monWindowCopy->setTextColor(qRgb(192, 0, 0));
-	else
-		monWindowCopy->setTextColor(qRgb(0, 0, 192));
-
-	monWindowCopy->textCursor().insertText(Msg);
-
-	if (old_cursor.hasSelection() || !is_scrolled_down)
-	{
-		// The user has selected text or scrolled away from the bottom: maintain position.
-		monWindowCopy->setTextCursor(old_cursor);
-		monWindowCopy->verticalScrollBar()->setValue(old_scrollbar_value);
-	}
-	else
-	{
-		// The user hasn't selected any text and the scrollbar is at the bottom: scroll to the bottom.
-		monWindowCopy->moveCursor(QTextCursor::End);
-		monWindowCopy->verticalScrollBar()->setValue(monWindowCopy->verticalScrollBar()->maximum());
-	}
-
-	free(Msg);
-}
-
-
-// I think this does the waterfall
-
-typedef struct TRGBQ_t
-{
-	Byte b, g, r, re;
-
-} TRGBWQ;
-
-typedef struct tagRECT
-{
-	int    left;
-	int    top;
-	int    right;
-	int    bottom;
-} RECT;
-
-unsigned int RGBWF[256] ;
-
-
-extern "C" void init_raduga()
-{
-	Byte offset[6] = {0, 51, 102, 153, 204};
-	Byte i, n;
-
-	for (n = 0; n < 52; n++)
-	{
-		i = n * 5;
-
-		RGBWF[n + offset[0]] = qRgb(0, 0, i);
-		RGBWF[n + offset[1]] = qRgb(0, i, 255);
-		RGBWF[n + offset[2]] = qRgb(0, 255, 255 - i);
-		RGBWF[n + offset[3]] = qRgb(1, 255, 0);
-		RGBWF[n + offset[4]] = qRgb(255, 255 - 1, 0);
-	}
-}
-
-extern "C" int nonGUIMode;
-
-
-// This draws the Frequency Scale on Waterfall
-
-extern "C" void wf_Scale(int Chan)
-{
-	if (nonGUIMode)
-		return;
-
-	float k;
-	int maxfreq, x, i;
-	char Textxx[20];
-	QImage * bm = Header[Chan];
-
-	QPainter qPainter(bm);
-	qPainter.setBrush(Qt::black);
-	qPainter.setPen(Qt::white);
-
-	maxfreq = roundf(RX_Samplerate*0.005);
-	k = 100 * fft_size / RX_Samplerate;
-
-	if (Chan == 0)
-		sprintf(Textxx, "Left");
-	else
-		sprintf(Textxx, "Right");
-
-	qPainter.drawText(2, 1,
-		100, 20, 0, Textxx);
-
-	for (i = 0; i < maxfreq; i++)
-	{
-		x = round(k*i);
-		if (x < 1025)
-		{
-			if ((i % 5) == 0)
-				qPainter.drawLine(x, 20, x, 13);
-			else
-				qPainter.drawLine(x, 20, x, 16);
-
-			if ((i % 10) == 0)
-			{
-				sprintf(Textxx, "%d", i * 100);
-
-				qPainter.drawText(x - 12, 1,
-					100, 20, 0, Textxx);
-			}
-		}
-	}
-	HeaderCopy[Chan]->setPixmap(QPixmap::fromImage(*bm));
-
-}
-
-// This draws the frequency Markers on the Waterfall
-
-
-void do_pointer(int waterfall)
-{
-	if (nonGUIMode)
-		return;
-
-	float x;
-
-	int x1, x2, k, pos1, pos2, pos3;
-	QImage * bm = Header[waterfall];
-
-	QPainter qPainter(bm);
-	qPainter.setBrush(Qt::NoBrush);
-	qPainter.setPen(Qt::white);
-
-	//	bm->fill(black);
-
-	qPainter.fillRect(0, 26, 1024, 9, Qt::black);
-
-	k = 29;
-	x = fft_size / RX_Samplerate;
-
-	// draw all enabled ports on the ports on this soundcard
-
-	// First Modem is always on the first waterfall
-	// If second is enabled it is on the first unless different
-	//		channel from first
-
-	for (int i = 0; i < 4; i++)
-	{
-		if (UsingBothChannels == 0)
-		{
-			// Only One Waterfall. If first chan is 
-
-			if ((waterfall == 0 && soundChannel[i] == RIGHT) || (waterfall == 1 && soundChannel[i] == LEFT))
-				return;
-		}
-
-		if (soundChannel[i] == 0)
-			continue;
-
-
-		if (UsingBothChannels == 1)
-			if ((waterfall == 0 && soundChannel[i] == RIGHT) || (waterfall == 1 && soundChannel[i] == LEFT))
-				continue;
-
-		pos1 = roundf(((rxOffset + chanOffset[i] + rx_freq[i]) - 0.5*rx_shift[i])*x) - 5;
-		pos2 = roundf(((rxOffset + chanOffset[i] + rx_freq[i]) + 0.5*rx_shift[i])*x) - 5;
-		pos3 = roundf((rxOffset + chanOffset[i] + rx_freq[i]) * x);
-		x1 = pos1 + 5;
-		x2 = pos2 + 5;
-
-		qPainter.setPen(Qt::white);
-		qPainter.drawLine(x1, k, x2, k);
-		qPainter.drawLine(x1, k - 3, x1, k + 3);
-		qPainter.drawLine(x2, k - 3, x2, k + 3);
-		qPainter.drawLine(pos3, k - 3, pos3, k + 3);
-
-		if (rxOffset || chanOffset[i])
-		{
-			// Draw TX posn if rxOffset used
-
-			pos3 = roundf(rx_freq[i] * x);
-			qPainter.setPen(Qt::magenta);
-			qPainter.drawLine(pos3, k - 3, pos3, k + 3);
-			qPainter.drawLine(pos3, k - 3, pos3, k + 3);
-			qPainter.drawLine(pos3 - 2, k - 3, pos3 + 2, k - 3);
-
-		}
-	}
-	HeaderCopy[waterfall]->setPixmap(QPixmap::fromImage(*bm));
-}
-
-void wf_pointer(int snd_ch)
-{
-	UNUSED(snd_ch);
-
-	do_pointer(0);
-	do_pointer(1);
-//	do_pointer(2);
-//	do_pointer(3);
-}
-
-
-void doWaterfallThread(void * param);
-
-/*
-#ifdef WIN32
-
-#define pthread_t uintptr_t
-
-extern "C" uintptr_t _beginthread(void(__cdecl *start_address)(void *), unsigned stack_size, void *arglist);
-
-#else
-
-#include <pthread.h>
-
-extern "C" pthread_t _beginthread(void(*start_address)(void *), unsigned stack_size, void * arglist)
-{
-	pthread_t thread;
-
-	if (pthread_create(&thread, NULL, (void * (*)(void *))start_address, (void*)arglist) != 0)
-		perror("New Thread");
-	else
-		pthread_detach(thread);
-
-	return thread;
-}
-
-#endif
-*/
-extern "C" void doWaterfall(int snd_ch)
-{
-	if (nonGUIMode)
-		return;
-
-	if (Closing)
-		return;
-
-//	if (multiCore)			// Run modems in separate threads
-//		_beginthread(doWaterfallThread, 0, xx);
-//	else
-		doWaterfallThread((void *)(size_t)snd_ch);
-
-}
-
-
-extern "C" float aFFTAmpl[1024];
-
-void doWaterfallThread(void * param)
-{
-	int snd_ch = (int)(size_t)param;
-
-	QImage * bm = Waterfall[snd_ch];
-	
-	word  i, wid;
-	single  mag;
-	UCHAR * p;
-	UCHAR Line[4096];
-
-	int lineLen;
-	word  hfft_size;
-	Byte  n;
-	float RealOut[4096] = { 0 };
-	float ImagOut[4096];
-
-	QRegion exposed;
-
-	hfft_size = fft_size / 2;
-
-	// I think an FFT should produce n/2 bins, each of Samp/n Hz
-	// Looks like my code only works with n a power of 2
-
-	// So can use 1024 or 4096. 1024 gives 512 bins of 11.71875 and a 512 pixel 
-	// display (is this enough?)
-
-	// This does 2048
-
-	if (0)	//RSID_WF
-	{
-		// Use the Magnitudes in float aFFTAmpl[RSID_FFT_SIZE];
-
-		for (i = 0; i < hfft_size; i++)
-		{
-			mag = aFFTAmpl[i];
-
-			mag *= 0.00000042f;
-
-			if (mag < 0.00001f)
-				mag = 0.00001f;
-
-			if (mag > 1.0f)
-				mag = 1.0f;
-
-			mag = 22 * log2f(mag) + 255;
-
-			if (mag < 0)
-				mag = 0;
-
-			fft_disp[snd_ch][i] = round(mag);
-		}
-	}
-	else
-	{
-		dofft(&fft_buf[snd_ch][0], RealOut, ImagOut);
-
-		//	FourierTransform(1024, &fft_buf[snd_ch][0], RealOut, ImagOut, 0);
-
-		for (i = 0; i < hfft_size; i++)
-		{
-			//mag: = ComplexMag(fft_d[i])*0.00000042;
-
-	//		mag = sqrtf(powf(RealOut[i], 2) + powf(ImagOut[i], 2)) * 0.00000042f;
-
-			mag = powf(RealOut[i], 2);
-			mag += powf(ImagOut[i], 2);
-			mag = sqrtf(mag);
-			mag *= 0.00000042f;
-
-
-			if (mag > MaxMagOut)
-			{
-				MaxMagOut = mag;
-				MaxMagIndex = i;
-			}
-
-			if (mag < 0.00001f)
-				mag = 0.00001f;
-
-			if (mag > 1.0f)
-				mag = 1.0f;
-
-			mag = 22 * log2f(mag) + 255;
-
-			if (mag < 0)
-				mag = 0;
-
-			MagOut[i] = mag;
-			fft_disp[snd_ch][i] = round(mag);
-		}
-	}
-
-
-
-	/*
-		for (i = 0; i < hfft_size; i++)
-			fft[i] = (powf(RealOut[i], 2) + powf(ImagOut[i], 2));
-
-		for (i = 0; i < hfft_size; i++)
-		{
-			if (fft[i] > max)
-			{
-				max = fft[i];
-				imax = i;
-			}
-		}
-
-		if (max > 0)
-		{
-			for (i = 0; i < hfft_size; i++)
-				fft[i] = fft[i] / max;
-		}
-
-
-		for (i = 0; i < hfft_size; i++)
-		{
-			mag = fft[i];
-
-			if (mag < 0.00001f)
-				mag = 0.00001f;
-
-			if (mag > 1.0f)
-				mag = 1.0f;
-
-			mag = 22 * log2f(mag) + 255;
-
-			if (mag < 0)
-				mag = 0;
-
-			fft_disp[snd_ch][i] = round(mag);
-		}
-
-		*/
-
-	//	bm[snd_ch].Canvas.CopyRect(d, bm[snd_ch].canvas, s)
-
-	//pm->scroll(0, 1, 0, 0, 1024, 80, &exposed);
-
-	// Each bin is 12000 /2048 = 5.859375
-	// I think we plot at 6 Hz per pixel.
-
-	wid = bm->width();
-	if (wid > hfft_size)
-		wid = hfft_size;
-
-	wid = wid - 1;
-
-	p = Line;
-	lineLen = bm->bytesPerLine();
-
-	if (wid > lineLen / 4)
-		wid = lineLen / 4;
-
-	if (raduga == DISP_MONO)
-	{
-		for (i = 0; i < wid; i++)
-		{
-			n = fft_disp[snd_ch][i];
-			*(p++) = n;					// all colours the same
-			*(p++) = n;
-			*(p++) = n;
-			p++;
-		}
-	}
-	else
-	{
-		for (i = 0; i < wid; i++)
-		{
-			n = fft_disp[snd_ch][i];
-
-		memcpy(p, &RGBWF[n], 4);
-			p += 4;
-		}
-	}
-
-	// Scroll
-
-	int TopLine = NextWaterfallLine[snd_ch];
-
-	// Write line to cyclic buffer then draw starting with the line just written
-
-	memcpy(&WaterfallLines[snd_ch][NextWaterfallLine[snd_ch]++][0], Line, 4096);
-	if (NextWaterfallLine[snd_ch] > 79)
-		NextWaterfallLine[snd_ch] = 0;
-
-	for (int j = 79; j > 0; j--)
-	{
-		p = bm->scanLine(j);
-		memcpy(p, &WaterfallLines[snd_ch][TopLine][0], lineLen);
-		TopLine++;
-		if (TopLine > 79)
-			TopLine = 0;
-	}
-
-	WaterfallCopy[snd_ch]->setPixmap(QPixmap::fromImage(*bm));
-	//	WaterfallCopy[snd_ch - 1]->setPixmap(*pm);
-		//	WaterfallCopy[1]->setPixmap(QPixmap::fromImage(*bm));
-
-}
-
-
-
-void QtSoundModem::changeEvent(QEvent* e)
-{
-	if (e->type() == QEvent::WindowStateChange)
-	{
-		QWindowStateChangeEvent* ev = static_cast<QWindowStateChangeEvent*>(e);
-
-		qDebug() << windowState();
-
-		if (!(ev->oldState() & Qt::WindowMinimized) && windowState() & Qt::WindowMinimized)
-		{
-			if (trayIcon)
-				setVisible(false);
-		}
-//		if (!(ev->oldState() != Qt::WindowNoState) && windowState() == Qt::WindowNoState)
-//		{
-//			QMessageBox::information(this, "", "Window has been restored");
-//		}
-
-	}
-	QWidget::changeEvent(e);
-}
-
-#include <QCloseEvent>
-
-void QtSoundModem::closeEvent(QCloseEvent *event)
-{
-	UNUSED(event);
-
-	QSettings mysettings("QtSoundModem.ini", QSettings::IniFormat);
-	mysettings.setValue("geometry", QWidget::saveGeometry());
-	mysettings.setValue("windowState", saveState());
-
-	Closing = TRUE;
-	qDebug() << "Closing";
-
-	QThread::msleep(100);
-}
-
-	
-QtSoundModem::~QtSoundModem()
-{
-	qDebug() << "Saving Settings";
-		
-	QSettings mysettings("QtSoundModem.ini", QSettings::IniFormat);
-	mysettings.setValue("geometry", saveGeometry());
-	mysettings.setValue("windowState", saveState());
-	
-	saveSettings();	
-	Closing = TRUE;
-	qDebug() << "Closing";
-
-	QThread::msleep(100);
-}
-
-extern "C" void QSleep(int ms)
-{
-	QThread::msleep(ms);
-}
-
-int upd_time = 30;
-
-void QtSoundModem::show_grid()
-{
-	// This refeshes the session list
-
-	int  snd_ch, i, num_rows, row_idx;
-	QTableWidgetItem *item;
-	const char * msg;
-
-	int  speed_tx, speed_rx;
-
-	if (grid_time < 10)
-	{
-		grid_time++;
-		return;
-	}
-
-	grid_time = 0;
-
-	//label7.Caption = inttostr(stat_r_mem); mem_arq
-
-	num_rows = 0;
-	row_idx = 0;
-
-	for (snd_ch = 0; snd_ch < 4; snd_ch++)
-	{
-		for (i = 0; i < port_num; i++)
-		{
-			if (AX25Port[snd_ch][i].status != STAT_NO_LINK)
-				num_rows++;
-		}
-	}
-
-	if (num_rows == 0)
-	{
-		sessionTable->clearContents();
-		sessionTable->setRowCount(0);
-		sessionTable->setRowCount(1);
-	}
-	else
-		sessionTable->setRowCount(num_rows);
-
-
-	for (snd_ch = 0; snd_ch < 4; snd_ch++)
-	{
-		for (i = 0; i < port_num; i++)
-		{
-			if (AX25Port[snd_ch][i].status != STAT_NO_LINK)
-			{
-				switch (AX25Port[snd_ch][i].status)
-				{
-				case STAT_NO_LINK:
-
-					msg = "No link";
-					break;
-
-				case STAT_LINK:
-
-					msg = "Link";
-					break;
-
-				case STAT_CHK_LINK:
-
-					msg = "Chk link";
-					break;
-
-				case STAT_WAIT_ANS:
-
-					msg = "Wait ack";
-					break;
-
-				case STAT_TRY_LINK:
-
-					msg = "Try link";
-					break;
-
-				case STAT_TRY_UNLINK:
-
-					msg = "Try unlink";
-				}
-
-
-				item = new QTableWidgetItem((char *)AX25Port[snd_ch][i].mycall);
-				sessionTable->setItem(row_idx, 0, item);
-
-				item = new QTableWidgetItem(AX25Port[snd_ch][i].kind);
-				sessionTable->setItem(row_idx, 11, item);
-
-				item = new QTableWidgetItem((char *)AX25Port[snd_ch][i].corrcall);
-				sessionTable->setItem(row_idx, 1, item);
-
-				item = new QTableWidgetItem(msg);
-				sessionTable->setItem(row_idx, 2, item);
-
-				item = new QTableWidgetItem(QString::number(AX25Port[snd_ch][i].info.stat_s_pkt));
-				sessionTable->setItem(row_idx, 3, item);
-
-				item = new QTableWidgetItem(QString::number(AX25Port[snd_ch][i].info.stat_s_byte));
-				sessionTable->setItem(row_idx, 4, item);
-
-				item = new QTableWidgetItem(QString::number(AX25Port[snd_ch][i].info.stat_r_pkt));
-				sessionTable->setItem(row_idx, 5, item);
-
-				item = new QTableWidgetItem(QString::number(AX25Port[snd_ch][i].info.stat_r_byte));
-				sessionTable->setItem(row_idx, 6, item);
-
-				item = new QTableWidgetItem(QString::number(AX25Port[snd_ch][i].info.stat_r_fc));
-				sessionTable->setItem(row_idx, 7, item);
-
-				item = new QTableWidgetItem(QString::number(AX25Port[snd_ch][i].info.stat_fec_count));
-				sessionTable->setItem(row_idx, 8, item);
-
-				if (grid_timer != upd_time)
-					grid_timer++;
-				else
-				{
-					grid_timer = 0;
-					speed_tx = round(abs(AX25Port[snd_ch][i].info.stat_s_byte - AX25Port[snd_ch][i].info.stat_l_s_byte) / upd_time);
-					speed_rx = round(abs(AX25Port[snd_ch][i].info.stat_r_byte - AX25Port[snd_ch][i].info.stat_l_r_byte) / upd_time);
-
-					item = new QTableWidgetItem(QString::number(speed_tx));
-					sessionTable->setItem(row_idx, 9, item);
-
-					item = new QTableWidgetItem(QString::number(speed_rx));
-					sessionTable->setItem(row_idx, 10, item);
-
-					AX25Port[snd_ch][i].info.stat_l_r_byte = AX25Port[snd_ch][i].info.stat_r_byte;
-					AX25Port[snd_ch][i].info.stat_l_s_byte = AX25Port[snd_ch][i].info.stat_s_byte;	
-				}
-
-				row_idx++;
-			}
-		}
-	}
-}
-
-// "Copy on Select" Code
-
-void QtSoundModem::onTEselectionChanged()
-{
-	QTextEdit * x = static_cast<QTextEdit*>(QObject::sender());
-	x->copy();
-}
-
diff --git a/QtSoundModem.h b/QtSoundModem.h
index 1f0d6e5..626ddd9 100644
--- a/QtSoundModem.h
+++ b/QtSoundModem.h
@@ -29,7 +29,7 @@ public:
 	~QtSoundModem();
 
 	void RefreshWaterfall(int snd_ch, unsigned char * Data);
-	void initWaterfall(int chan, int state);
+	void initWaterfall(int state);
 	void show_grid();
 	void checkforCWID();
 
@@ -112,3 +112,9 @@ protected:
 	bool eventFilter(QObject *obj, QEvent *event) override;
 };
 
+
+#define WaterfallDisplayPixels 80
+#define WaterfallHeaderPixels 38
+#define WaterfallTotalPixels WaterfallDisplayPixels + WaterfallHeaderPixels
+#define WaterfallImageHeight (WaterfallTotalPixels + WaterfallTotalPixels)
+
diff --git a/QtSoundModem.ui b/QtSoundModem.ui
index 22e2b7a..1d7b110 100644
--- a/QtSoundModem.ui
+++ b/QtSoundModem.ui
@@ -50,48 +50,6 @@
      </rect>
     </property>
    </widget>
-   <widget class="QLabel" name="WaterfallB">
-    <property name="geometry">
-     <rect>
-      <x>0</x>
-      <y>586</y>
-      <width>959</width>
-      <height>80</height>
-     </rect>
-    </property>
-    <property name="sizePolicy">
-     <sizepolicy hsizetype="Minimum" vsizetype="Minimum">
-      <horstretch>0</horstretch>
-      <verstretch>0</verstretch>
-     </sizepolicy>
-    </property>
-    <property name="minimumSize">
-     <size>
-      <width>600</width>
-      <height>80</height>
-     </size>
-    </property>
-    <property name="maximumSize">
-     <size>
-      <width>5000</width>
-      <height>100</height>
-     </size>
-    </property>
-    <property name="font">
-     <font>
-      <pointsize>8</pointsize>
-     </font>
-    </property>
-    <property name="frameShape">
-     <enum>QFrame::Box</enum>
-    </property>
-    <property name="frameShadow">
-     <enum>QFrame::Plain</enum>
-    </property>
-    <property name="text">
-     <string>Waterfall</string>
-    </property>
-   </widget>
    <widget class="QLabel" name="label_2">
     <property name="geometry">
      <rect>
@@ -121,25 +79,25 @@
      <number>1500</number>
     </property>
    </widget>
-   <widget class="QLabel" name="WaterfallA">
+   <widget class="QLabel" name="Waterfall">
     <property name="geometry">
      <rect>
       <x>80</x>
       <y>488</y>
       <width>881</width>
-      <height>80</height>
+      <height>100</height>
      </rect>
     </property>
     <property name="minimumSize">
      <size>
       <width>600</width>
-      <height>80</height>
+      <height>100</height>
      </size>
     </property>
     <property name="maximumSize">
      <size>
       <width>5000</width>
-      <height>100</height>
+      <height>250</height>
      </size>
     </property>
     <property name="font">
@@ -215,78 +173,6 @@
      <number>10</number>
     </property>
    </widget>
-   <widget class="QLabel" name="HeaderA">
-    <property name="geometry">
-     <rect>
-      <x>25</x>
-      <y>460</y>
-      <width>1076</width>
-      <height>38</height>
-     </rect>
-    </property>
-    <property name="minimumSize">
-     <size>
-      <width>600</width>
-      <height>10</height>
-     </size>
-    </property>
-    <property name="maximumSize">
-     <size>
-      <width>5000</width>
-      <height>100</height>
-     </size>
-    </property>
-    <property name="font">
-     <font>
-      <pointsize>8</pointsize>
-     </font>
-    </property>
-    <property name="frameShape">
-     <enum>QFrame::Box</enum>
-    </property>
-    <property name="frameShadow">
-     <enum>QFrame::Plain</enum>
-    </property>
-    <property name="text">
-     <string>Waterfall</string>
-    </property>
-   </widget>
-   <widget class="QLabel" name="HeaderB">
-    <property name="geometry">
-     <rect>
-      <x>10</x>
-      <y>560</y>
-      <width>1076</width>
-      <height>38</height>
-     </rect>
-    </property>
-    <property name="minimumSize">
-     <size>
-      <width>600</width>
-      <height>10</height>
-     </size>
-    </property>
-    <property name="maximumSize">
-     <size>
-      <width>5000</width>
-      <height>100</height>
-     </size>
-    </property>
-    <property name="font">
-     <font>
-      <pointsize>8</pointsize>
-     </font>
-    </property>
-    <property name="frameShape">
-     <enum>QFrame::Box</enum>
-    </property>
-    <property name="frameShadow">
-     <enum>QFrame::Plain</enum>
-    </property>
-    <property name="text">
-     <string>Waterfall</string>
-    </property>
-   </widget>
    <widget class="QTextEdit" name="monWindow">
     <property name="geometry">
      <rect>
diff --git a/QtSoundModem.vcxproj-DESKTOP-MHE5LO8.user b/QtSoundModem.vcxproj-DESKTOP-MHE5LO8.user
deleted file mode 100644
index a71d175..0000000
--- a/QtSoundModem.vcxproj-DESKTOP-MHE5LO8.user
+++ /dev/null
@@ -1,34 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <LocalDebuggerWorkingDirectory>C:\DevProgs\BPQ32\SMTest</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-    <LocalDebuggerCommandArguments>
-    </LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <LocalDebuggerWorkingDirectory>c:\devprogs\bpq32\SMSAT2</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-    <LocalDebuggerCommandArguments>&lt; d:\samples.wav</LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <LocalDebuggerWorkingDirectory>.\debug</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <LocalDebuggerWorkingDirectory>C:\DevProgs\BPQ32\SMSat</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <QtLastBackgroundBuild>2023-08-21T20:12:53.1523329Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="QtSettings">
-    <QtLastBackgroundBuild>2022-03-11T19:38:31.5906689Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <QtLastBackgroundBuild>2023-08-18T07:29:42.4175478Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="QtSettings">
-    <QtLastBackgroundBuild>2022-03-11T19:38:33.3845083Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-</Project>
\ No newline at end of file
diff --git a/QtSoundModem.vcxproj-HPLaptop.user b/QtSoundModem.vcxproj-HPLaptop.user
deleted file mode 100644
index 8995d93..0000000
--- a/QtSoundModem.vcxproj-HPLaptop.user
+++ /dev/null
@@ -1,34 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <LocalDebuggerWorkingDirectory>C:\Devprogs\bpq32\SMSat2</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-    <LocalDebuggerCommandArguments>
-    </LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <LocalDebuggerWorkingDirectory>c:\devprogs\bpq32\SMSAT2</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-    <LocalDebuggerCommandArguments>&lt; d:\samples.wav</LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <LocalDebuggerWorkingDirectory>C:\DevProgs\BPQ32\SMSat</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <LocalDebuggerWorkingDirectory>C:\DevProgs\BPQ32\SMSat</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <QtLastBackgroundBuild>2022-12-30T15:55:55.0433562Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="QtSettings">
-    <QtLastBackgroundBuild>2022-03-11T19:38:31.5906689Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-  <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <QtLastBackgroundBuild>2022-12-30T15:55:55.2283725Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="QtSettings">
-    <QtLastBackgroundBuild>2022-03-11T19:38:33.3845083Z</QtLastBackgroundBuild>
-  </PropertyGroup>
-</Project>
\ No newline at end of file
diff --git a/QtSoundModem.vcxproj.user b/QtSoundModem.vcxproj.user
index cf4a955..198fa38 100644
--- a/QtSoundModem.vcxproj.user
+++ b/QtSoundModem.vcxproj.user
@@ -11,7 +11,7 @@
     <LocalDebuggerCommandArguments>&lt; d:\samples.wav</LocalDebuggerCommandArguments>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <LocalDebuggerWorkingDirectory>.\debug</LocalDebuggerWorkingDirectory>
+    <LocalDebuggerWorkingDirectory>C:\DevProgs\BPQ32\SMTest</LocalDebuggerWorkingDirectory>
     <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
     <LocalDebuggerCommandArguments>-stylesheet StyleSheet.css</LocalDebuggerCommandArguments>
   </PropertyGroup>
@@ -20,15 +20,15 @@
     <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
   </PropertyGroup>
   <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <QtLastBackgroundBuild>2023-10-11T15:46:02.9163848Z</QtLastBackgroundBuild>
+    <QtLastBackgroundBuild>2023-10-13T13:21:39.9400374Z</QtLastBackgroundBuild>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="QtSettings">
-    <QtLastBackgroundBuild>2023-10-11T15:46:03.0449216Z</QtLastBackgroundBuild>
+    <QtLastBackgroundBuild>2023-10-13T13:21:40.0558471Z</QtLastBackgroundBuild>
   </PropertyGroup>
   <PropertyGroup Label="QtSettings" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <QtLastBackgroundBuild>2023-10-11T15:46:03.1725109Z</QtLastBackgroundBuild>
+    <QtLastBackgroundBuild>2023-10-13T13:21:40.2121547Z</QtLastBackgroundBuild>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="QtSettings">
-    <QtLastBackgroundBuild>2023-10-11T15:46:03.2783249Z</QtLastBackgroundBuild>
+    <QtLastBackgroundBuild>2023-10-13T13:21:40.4722944Z</QtLastBackgroundBuild>
   </PropertyGroup>
 </Project>
\ No newline at end of file
diff --git a/SMMain-DESKTOP-MHE5LO8.c b/SMMain-DESKTOP-MHE5LO8.c
deleted file mode 100644
index 8fc249e..0000000
--- a/SMMain-DESKTOP-MHE5LO8.c
+++ /dev/null
@@ -1,1433 +0,0 @@
-/*
-Copyright (C) 2019-2020 Andrei Kopanchuk UZ7HO
-
-This file is part of QtSoundModem
-
-QtSoundModem is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-QtSoundModem is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with QtSoundModem.  If not, see http://www.gnu.org/licenses
-
-*/
-
-// UZ7HO Soundmodem Port by John Wiseman G8BPQ
-
-#include "UZ7HOStuff.h"
-#include "fftw3.h"
-#include <time.h>
-#include "ecc.h"				// RS Constants
-#include "hidapi.h"
-#include <fcntl.h>
-#include <errno.h>
-#include <stdint.h>   
-
-BOOL KISSServ;
-int KISSPort;
-
-BOOL AGWServ;
-int AGWPort;
-
-int Number = 0;				// Number waiting to be sent
-
-int SoundIsPlaying = 0;
-int UDPSoundIsPlaying = 0;
-int Capturing = 0;
-
-extern unsigned short buffer[2][1200];
-extern int SoundMode;
-extern int needRSID[4];
-
-extern short * DMABuffer;
-
-unsigned short * SendtoCard(unsigned short * buf, int n);
-short * SoundInit();
-void DoTX(int Chan);
-void UDPPollReceivedSamples();
-
-
-extern int SampleNo;
-
-extern int pnt_change[5];				// Freq Changed Flag
-
-// fftw library interface
-
-
-fftwf_complex *in, *out;
-fftwf_plan p;
-
-int FFTSize = 4096;
-
-char * Wisdom;
-
-void initfft()
-{
-	fftwf_import_wisdom_from_string(Wisdom); 
-	fftwf_set_timelimit(30);
-
-#ifndef WIN32
-	printf("It may take up to 30 seconds for the program to start for the first time\n");
-#endif
-
-	in = (fftwf_complex*)fftwf_malloc(sizeof(fftwf_complex) * 10000);
-	out = (fftwf_complex*)fftwf_malloc(sizeof(fftwf_complex) * 10000);
-	p = fftwf_plan_dft_1d(FFTSize, in, out, FFTW_FORWARD, FFTW_PATIENT);
-
-	Wisdom = fftwf_export_wisdom_to_string();
-}
-
-void dofft(short * inp, float * outr, float * outi)
-{
-	int i;
-	
-	fftwf_complex * fft = in;
-
-	for (i = 0; i < FFTSize; i++)
-	{
-		fft[0][0] = inp[0] * 1.0f;
-		fft[0][1] = 0;
-		fft++;
-		inp++;
-	}
-
-	fftwf_execute(p); 
-
-	fft = out;
-
-	for (i = 0; i < FFTSize; i++)
-	{
-		outr[0] = fft[0][0];
-		outi[0] = fft[0][1];
-		fft++;
-		outi++;
-		outr++;
-	}
-}
-
-void freefft()
-{
-	fftwf_destroy_plan(p);
-	fftwf_free(in);
-	fftwf_free(out);
-}
-
-int nonGUIMode = 0;
-
-void soundMain()
-{
-	// non platform specific initialisation
-
-	platformInit();
-
-	// initialise fft library
-
-	RsCreate();				// RS code for MPSK
-
-	detector_init();
-	KISS_init();
-	ax25_init();
-	init_raduga();			// Set up waterfall colour table
-
-	initfft();
-
-	if (nonGUIMode)
-	{
-		Firstwaterfall = 0;
-		Secondwaterfall = 0;
-	}
-
-	OpenPTTPort();
-}
-
-
-void SampleSink(int LR, short Sample)
-{
-	// This version is passed samples one at a time, as we don't have
-	//	enough RAM in embedded systems to hold a full audio frame
-
-	// LR - 1 == Right Chan
-
-#ifdef TEENSY	
-		int work = Sample;
-		DMABuffer[Number++] = (work + 32768) >> 4; // 12 bit left justify
-#else
-	if (SCO)			// Single Channel Output - same to both L and R
-	{
-		DMABuffer[2 * Number] = Sample;
-		DMABuffer[1 + 2 * Number] = Sample;
-
-	}
-	else
-	{
-		if (LR)				// Right
-		{
-			DMABuffer[1 + 2 * Number] = Sample;
-			DMABuffer[2 * Number] = 0;
-		}
-		else
-		{
-			DMABuffer[2 * Number] = Sample;
-			DMABuffer[1 + 2 * Number] = 0;
-		}
-	}
-	if (using48000)
-	{
-		// Need to upsample to 48K. Try just duplicating sample
-
-		uint32_t * ptr = &DMABuffer[2 * Number];
-
-		*(&ptr[1]) = *(ptr);
-		*(&ptr[2]) = *(ptr);
-		*(&ptr[3]) = *(ptr);
-
-		Number += 3;
-	}
-	Number++;
-#endif
-		if (Number >= SendSize)
-		{
-			// send this buffer to sound interface
-
-			DMABuffer = SendtoCard(DMABuffer, SendSize);
-			Number = 0;
-		}
-	
-
-//	Last120[Last120Put++] = Sample;
-
-//	if (Last120Put == (intN + 1))
-//		Last120Put = 0;
-
-	SampleNo++;
-}
-
-
-void Flush()
-{
-	SoundFlush(Number);
-}
-
-int ipow(int base, int exp)
-{
-	int result = 1;
-	while (exp)
-	{
-		if (exp & 1)
-			result *= base;
-		exp >>= 1;
-		base *= base;
-	}
-
-	return result;
-}
-
-int NumberOfBitsNeeded(int PowerOfTwo)
-{
-	int i;
-
-	for (i = 0; i <= 16; i++)
-	{
-		if ((PowerOfTwo & ipow(2, i)) != 0)
-			return i;
-
-	}
-	return 0;
-}
-
-
-int ReverseBits(int Index, int NumBits)
-{
-	int i, Rev = 0;
-
-	for (i = 0; i < NumBits; i++)
-	{
-		Rev = (Rev * 2) | (Index & 1);
-		Index = Index / 2;
-	}
-
-	return Rev;
-}
-
-
-void FourierTransform(int NumSamples, short * RealIn, float * RealOut, float * ImagOut, int InverseTransform)
-{
-	float AngleNumerator;
-	unsigned char NumBits;
-
-	int i, j, K, n, BlockSize, BlockEnd;
-	float DeltaAngle, DeltaAr;
-	float Alpha, Beta;
-	float TR, TI, AR, AI;
-
-	if (InverseTransform)
-		AngleNumerator = -2.0f * M_PI;
-	else
-		AngleNumerator = 2.0f * M_PI;
-
-	NumBits = NumberOfBitsNeeded(NumSamples);
-
-	for (i = 0; i < NumSamples; i++)
-	{
-		j = ReverseBits(i, NumBits);
-		RealOut[j] = RealIn[i];
-		ImagOut[j] = 0.0f; // Not using i in ImageIn[i];
-	}
-
-	BlockEnd = 1;
-	BlockSize = 2;
-
-	while (BlockSize <= NumSamples)
-	{
-		DeltaAngle = AngleNumerator / BlockSize;
-		Alpha = sinf(0.5f * DeltaAngle);
-		Alpha = 2.0f * Alpha * Alpha;
-		Beta = sinf(DeltaAngle);
-
-		i = 0;
-
-		while (i < NumSamples)
-		{
-			AR = 1.0f;
-			AI = 0.0f;
-
-			j = i;
-
-			for (n = 0; n < BlockEnd; n++)
-			{
-				K = j + BlockEnd;
-				TR = AR * RealOut[K] - AI * ImagOut[K];
-				TI = AI * RealOut[K] + AR * ImagOut[K];
-				RealOut[K] = RealOut[j] - TR;
-				ImagOut[K] = ImagOut[j] - TI;
-				RealOut[j] = RealOut[j] + TR;
-				ImagOut[j] = ImagOut[j] + TI;
-				DeltaAr = Alpha * AR + Beta * AI;
-				AI = AI - (Alpha * AI - Beta * AR);
-				AR = AR - DeltaAr;
-				j = j + 1;
-			}
-			i = i + BlockSize;
-		}
-		BlockEnd = BlockSize;
-		BlockSize = BlockSize * 2;
-	}
-
-	if (InverseTransform)
-	{
-		//	Normalize the resulting time samples...
-
-		for (i = 0; i < NumSamples; i++)
-		{
-			RealOut[i] = RealOut[i] / NumSamples;
-			ImagOut[i] = ImagOut[i] / NumSamples;
-		}
-	}
-}
-
-
-
-int LastBusyCheck = 0;
-
-extern UCHAR CurrentLevel;
-
-#ifdef PLOTSPECTRUM		
-float dblMagSpectrum[206];
-float dblMaxScale = 0.0f;
-extern UCHAR Pixels[4096];
-extern UCHAR * pixelPointer;
-#endif
-
-extern int blnBusyStatus;
-BusyDet = 5;
-
-#define PLOTWATERFALL
-
-int WaterfallActive = 1;
-int SpectrumActive;
-
-float BinSize;
-
-extern int intLastStart;
-extern int intLastStop;
-
-void SMSortSignals2(float * dblMag, int intStartBin, int intStopBin, int intNumBins, float *  dblAVGSignalPerBin, float *  dblAVGBaselinePerBin);
-
-
-BOOL SMBusyDetect3(float * dblMag, int intStart, int intStop)        // this only called while searching for leader ...once leader detected, no longer called.
-{
-	// First sort signals and look at highes signals:baseline ratio..
-
-	float dblAVGSignalPerBinNarrow, dblAVGSignalPerBinWide, dblAVGBaselineNarrow, dblAVGBaselineWide;
-	float dblSlowAlpha = 0.2f;
-	float dblAvgStoNNarrow = 0, dblAvgStoNWide = 0;
-	int intNarrow = 8;  // 8 x 11.72 Hz about 94 z
-	int intWide = ((intStop - intStart) * 2) / 3; //* 0.66);
-	int blnBusy = FALSE;
-	int  BusyDet4th = BusyDet * BusyDet * BusyDet * BusyDet;
-
-	// First sort signals and look at highest signals:baseline ratio..
-	// First narrow band (~94Hz)
-
-	SMSortSignals2(dblMag, intStart, intStop, intNarrow, &dblAVGSignalPerBinNarrow, &dblAVGBaselineNarrow);
-
-	if (intLastStart == intStart && intLastStop == intStop)
-		dblAvgStoNNarrow = (1 - dblSlowAlpha) * dblAvgStoNNarrow + dblSlowAlpha * dblAVGSignalPerBinNarrow / dblAVGBaselineNarrow;
-	else
-	{
-		// This initializes the Narrow average after a bandwidth change
-
-		dblAvgStoNNarrow = dblAVGSignalPerBinNarrow / dblAVGBaselineNarrow;
-		intLastStart = intStart;
-		intLastStop = intStop;
-	}
-
-	// Wide band (66% of current bandwidth)
-
-	SMSortSignals2(dblMag, intStart, intStop, intWide, &dblAVGSignalPerBinWide, &dblAVGBaselineWide);
-
-	if (intLastStart == intStart && intLastStop == intStop)
-		dblAvgStoNWide = (1 - dblSlowAlpha) * dblAvgStoNWide + dblSlowAlpha * dblAVGSignalPerBinWide / dblAVGBaselineWide;
-	else
-	{
-		// This initializes the Wide average after a bandwidth change
-
-		dblAvgStoNWide = dblAVGSignalPerBinWide / dblAVGBaselineWide;
-		intLastStart = intStart;
-		intLastStop = intStop;
-	}
-
-	// Preliminary calibration...future a function of bandwidth and BusyDet.
-
-
-	blnBusy = (dblAvgStoNNarrow > (3 + 0.008 * BusyDet4th)) || (dblAvgStoNWide > (5 + 0.02 * BusyDet4th));
-
-//	if (BusyDet == 0)
-//		blnBusy = FALSE;		// 0 Disables check ?? Is this the best place to do this?
-
-//	WriteDebugLog(LOGDEBUG, "Busy %d Wide %f Narrow %f", blnBusy, dblAvgStoNWide, dblAvgStoNNarrow); 
-
-	return blnBusy;
-}
-
-extern int compare(const void *p1, const void *p2);
-
-void SMSortSignals2(float * dblMag, int intStartBin, int intStopBin, int intNumBins, float *  dblAVGSignalPerBin, float *  dblAVGBaselinePerBin)
-{
-	// puts the top intNumber of bins between intStartBin and intStopBin into dblAVGSignalPerBin, the rest into dblAvgBaselinePerBin
-	// for decent accuracy intNumBins should be < 75% of intStopBin-intStartBin)
-
-	// This version uses a native sort function which is much faster and reduces CPU loading significantly on wide bandwidths. 
-
-	float dblSort[8192];
-	float dblSum1 = 0, dblSum2 = 0;
-	int numtoSort = (intStopBin - intStartBin) + 1, i;
-
-	memcpy(dblSort, &dblMag[intStartBin], numtoSort * sizeof(float));
-
-	qsort((void *)dblSort, numtoSort, sizeof(float), compare);
-
-	for (i = numtoSort - 1; i >= 0; i--)
-	{
-		if (i >= (numtoSort - intNumBins))
-			dblSum1 += dblSort[i];
-		else
-			dblSum2 += dblSort[i];
-	}
-
-	*dblAVGSignalPerBin = dblSum1 / intNumBins;
-	*dblAVGBaselinePerBin = dblSum2 / (intStopBin - intStartBin - intNumBins - 1);
-}
-
-
-
-void SMUpdateBusyDetector(int LR, float * Real, float *Imag)
-{
-	// Energy based detector for each channel.
-	// Fed from FFT generated for waterfall display
-	// FFT size is 4096
-
-	float dblMag[4096];
-
-	static BOOL blnLastBusyStatus[4];
-
-	float dblMagAvg = 0;
-	int intTuneLineLow, intTuneLineHi, intDelta;
-	int i, chan;
-
-	return;
-
-	if (Now - LastBusyCheck < 100)	// ??
-		return;
-
-	LastBusyCheck = Now;
-
-	// We need to run busy test on the frequncies used by each modem.
-
-	for (chan = 0; chan < 4; chan++)
-	{
-		int Low, High, Start, End;
-
-		if (soundChannel[chan] != (LR + 1))	// on this side of soundcard 
-			continue;
-
-		Low = tx_freq[chan] - txbpf[chan] / 2;
-		High = tx_freq[chan] + txbpf[chan] / 2;
-
-		// BinSize is width of each fft bin in Hz
-
-		Start = (Low / BinSize);		// First and last bins to process
-		End = (High / BinSize);
-
-
-		for (i = Start; i < End; i++)
-		{
-			dblMag[i] = powf(Real[i], 2) + powf(Imag[i], 2);	 // first pass
-			dblMagAvg += dblMag[i];
-		}
-
-		blnBusyStatus = SMBusyDetect3(dblMag, Start, End);
-
-		if (blnBusyStatus && !blnLastBusyStatus[chan])
-		{
-			Debugprintf("Ch %d Busy True", chan);
-		}
-		else if (blnLastBusyStatus[chan] && !blnBusyStatus)
-		{
-			Debugprintf("Ch %d Busy False", chan);
-		}
-		//    stcStatus.Text = "FALSE"
-		//    queTNCStatus.Enqueue(stcStatus)
-		//    'Debug.WriteLine("BUSY FALSE @ " & Format(DateTime.UtcNow, "HH:mm:ss"))
-
-		blnLastBusyStatus[chan] = blnBusyStatus;
-	}
-}
-
-
-extern short rawSamples[2400];	// Get Frame Type need 2400 and we may add 1200
-int rawSamplesLength = 0;
-extern int maxrawSamplesLength;
-
-void ProcessNewSamples(short * Samples, int nSamples)
-{
-	if (SoundIsPlaying == FALSE && UDPSoundIsPlaying == FALSE)
-		BufferFull(Samples, nSamples);
-};
-
-void doCalib(int Chan, int Act)
-{
-	if (Chan == 0 && calib_mode[1])
-		return;						
-	
-	if (Chan == 1 && calib_mode[0])
-		return;
-
-	calib_mode[Chan] = Act;
-
-	if (Act == 0)
-	{
-		tx_status[Chan] = TX_SILENCE;		// Stop TX
-		Flush();
-		RadioPTT(Chan, 0);
-		Debugprintf("Stop Calib");
-	}
-}
-
-int Freq_Change(int Chan, int Freq)
-{
-	int low, high;
-
-	low = round(rx_shift[1] / 2 + RCVR[Chan] * rcvr_offset[Chan] + 1);
-	high = round(RX_Samplerate / 2 - (rx_shift[Chan] / 2 + RCVR[Chan] * rcvr_offset[Chan]));
-
-	if (Freq < low)
-		return rx_freq[Chan];				// Dont allow change
-
-	if (Freq > high)
-		return rx_freq[Chan];				// Dont allow change
-
-	rx_freq[Chan] = Freq;
-	tx_freq[Chan] = Freq;
-
-	pnt_change[Chan] = TRUE;
-	wf_pointer(soundChannel[Chan]);
-
-	return Freq;
-}
-
-void MainLoop()
-{
-	// Called by background thread every 10 ms (maybe)
-
-	// Actually we may have two cards
-	
-	// Original only allowed one channel per card.
-	// I think we should be able to run more, ie two or more
-	// modems on same soundcard channel
-	
-	// So All the soundcard stuff will need to be generalised
-
-	if (UDPServ)
-		UDPPollReceivedSamples();
-
-	if (SoundMode == 3)
-		UDPPollReceivedSamples();
-	else
-		PollReceivedSamples();
-
-
-	for (int i = 0; i < 4; i++)
-	{
-		if (modem_mode[i] == MODE_ARDOP)
-		{
-			chk_dcd1(i, 512);
-		}
-	}
-	DoTX(0);
-	DoTX(1);
-	DoTX(2);
-	DoTX(3);
-
-}
-
-int ARDOPSendToCard(int Chan, int Len)
-{
-	// Send Next Block of samples to the soundcard
-
-
-	short * in = &ARDOPTXBuffer[Chan][ARDOPTXPtr[Chan]];		// Enough to hold whole frame of samples
-	short * out = DMABuffer;
-
-	int LR = modemtoSoundLR[Chan];
-
-	int i;
-
-	for (i = 0; i < Len; i++)
-	{
-		if (SCO)			// Single Channel Output - same to both L and R
-		{
-			*out++ = *in;
-			*out++ = *in++;
-		}
-		else
-		{
-			if (LR)				// Right
-			{
-				*out++ = 0;
-				*out++ = *in++;
-			}
-			else
-			{
-				*out++ = *in++;
-				*out++ = 0;
-			}
-		}
-	}
-
-	DMABuffer = SendtoCard(DMABuffer, Len);
-
-	ARDOPTXPtr[Chan] += Len;
-
-	// See if end of buffer
-
-	if (ARDOPTXPtr[Chan] > ARDOPTXLen[Chan])
-		return 1;
-
-	return 0;
-}
-void DoTX(int Chan)
-{
-	// This kicks off a send sequence or calibrate
-
-//	printtick("dotx");
-
-	if (calib_mode[Chan])
-	{
-		// Maybe new calib or continuation
-
-		if (pnt_change[Chan])
-		{
-			make_core_BPF(Chan, rx_freq[Chan], bpf[Chan]);
-			make_core_TXBPF(Chan, tx_freq[Chan], txbpf[Chan]);
-			pnt_change[Chan] = FALSE;
-		}
-		
-		// Note this may block in SendtoCard
-
-		modulator(Chan, tx_bufsize);
-		return;
-	}
-
-	// I think we have to detect NO_DATA here and drop PTT and return to SILENCE
-
-	if (tx_status[Chan] == TX_NO_DATA)
-	{
-		Flush();
-		Debugprintf("TX Complete");
-		RadioPTT(0, 0);
-		Continuation[Chan] = 0;
-
-		tx_status[Chan] = TX_SILENCE;
-
-		// We should now send any ackmode acks as the channel is now free for dest to reply
-
-		sendAckModeAcks(Chan);
-	}
-
-	if (tx_status[Chan] != TX_SILENCE)
-	{
-		// Continue the send
-
-		if (modem_mode[Chan] == MODE_ARDOP || modem_mode[Chan] == MODE_RUH)
-		{
-//			if (SeeIfCardBusy())
-//				return 0;
-
-			if (ARDOPSendToCard(Chan, SendSize) == 1)
-			{
-				// End of TX
-
-				Number = 0;
-				Flush();
-
-				// See if more to send. If so, don't drop PTT
-
-				if (all_frame_buf[Chan].Count)
-				{
-					SoundIsPlaying = TRUE;
-					Number = 0;
-
-					Continuation[Chan] = 1;
-
-					Debugprintf("TX Continuing");
-
-					string * myTemp = Strings(&all_frame_buf[Chan], 0);			// get message
-					string * tx_data;
-
-					if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-					{
-						// Save copy then copy data up 3 bytes
-
-						Add(&KISS_acked[Chan], duplicateString(myTemp));
-
-						mydelete(myTemp, 0, 3);
-						myTemp->Length -= sizeof(void *);
-					}
-					else
-					{
-						// Just remove control 
-
-						mydelete(myTemp, 0, 1);
-					}
-
-					tx_data = duplicateString(myTemp);		// so can free original below
-
-					Delete(&all_frame_buf[Chan], 0);			// This will invalidate temp
-
-					AGW_AX25_frame_analiz(Chan, FALSE, tx_data);
-
-					put_frame(Chan, tx_data, "", TRUE, FALSE);
-
-					if (modem_mode[Chan] == MODE_ARDOP)
-						PktARDOPEncode(tx_data->Data, tx_data->Length - 2, Chan);
-					else
-						RUHEncode(tx_data->Data, tx_data->Length - 2, Chan);
-
-					freeString(tx_data);
-
-					// Samples are now in DMABuffer = Send first block
-
-					DMABuffer = SoundInit();
-
-					ARDOPSendToCard(Chan, SendSize);
-					tx_status[Chan] = TX_FRAME;
-					return;
-				}
-
-				Debugprintf("TX Complete");
-				RadioPTT(0, 0);
-				Continuation[Chan] = 0;
-
-				tx_status[Chan] = TX_SILENCE;
-
-				// We should now send any ackmode acks as the channel is now free for dest to reply
-			}
-
-			return;
-		}
-
-		modulator(Chan, tx_bufsize); 
-		return;
-	}
-
-	if (SoundIsPlaying || UDPSoundIsPlaying)
-		return;
-
-	// Not doing anything so see if we have anything new to send
-
-	// See if frequency has changed
-
-	if (pnt_change[Chan])
-	{
-		make_core_BPF(Chan, rx_freq[Chan], bpf[Chan]);
-		make_core_TXBPF(Chan, tx_freq[Chan], txbpf[Chan]);
-		pnt_change[Chan] = FALSE;
-	}
-
-	// See if we need an RSID
-
-	if (needRSID[Chan])
-	{
-		needRSID[Chan] = 0;
-
-		// Note this may block in SampleSink
-
-		Debugprintf("Sending RSID");
-		sendRSID(Chan, all_frame_buf[Chan].Count == 0);
-		return;
-	}
-
-	if (all_frame_buf[Chan].Count == 0)
-		return;
-
-	// Start a new send. modulator should handle TXD etc
-
-	Debugprintf("TX Start");
-	SampleNo = 0;
-
-	SoundIsPlaying = TRUE;
-	RadioPTT(Chan, 1);
-	Number = 0;
-
-	if (modem_mode[Chan] == MODE_ARDOP)
-	{
-		// I think ARDOP will have to generate a whole frame of samples
-		// then send them out a bit at a time to avoid stopping here for
-		// possibly 10's of seconds
-
-		// Can do this here as unlike normal ardop we don't need to run on Teensy
-		// to 12000 sample rate we need either 24K or 48K per second, depending on
-		// where we do the stereo mux. 
-
-		// Slowest rate is 50 baud, so a 255 byte packet would take about a minute
-		// allowing for RS overhead. Not really realistic put perhaps should be possible.
-		// RAM isn't an issue so maybe allocate 2 MB. 
-
-		// ?? Should we allow two ARDOP modems - could make sense if we can run sound
-		// card channels independently
-
-		string * myTemp = Strings(&all_frame_buf[Chan], 0);			// get message
-		string * tx_data;
-
-		if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-		{
-			// Save copy then copy data up 3 bytes
-
-			Add(&KISS_acked[Chan], duplicateString(myTemp));
-
-			mydelete(myTemp, 0, 3);
-			myTemp->Length -= sizeof(void *);
-		}
-		else
-		{
-			// Just remove control 
-
-			mydelete(myTemp, 0, 1);
-		}
-
-		tx_data = duplicateString(myTemp);		// so can free original below
-
-		Delete(&all_frame_buf[Chan], 0);			// This will invalidate temp
-
-		AGW_AX25_frame_analiz(Chan, FALSE, tx_data);
-
-		put_frame(Chan, tx_data, "", TRUE, FALSE);
-
-		PktARDOPEncode(tx_data->Data, tx_data->Length - 2, Chan);
-
-		freeString(tx_data);
-
-		// Samples are now in DMABuffer = Send first block
-
-		ARDOPSendToCard(Chan, SendSize);
-		tx_status[Chan] = TX_FRAME;
-
-	}
-	else if (modem_mode[Chan] == MODE_RUH)
-	{
-		// Same as for ARDOP. Generate a whole frame of samples 
-		// then send them out a bit at a time to avoid stopping here
-
-		// We allow two RUH modems
-
-		string * myTemp = Strings(&all_frame_buf[Chan], 0);			// get message
-		string * tx_data;
-
-		if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-		{
-			// Save copy then copy data up 3 bytes
-
-			Add(&KISS_acked[Chan], duplicateString(myTemp));
-
-			mydelete(myTemp, 0, 3);
-			myTemp->Length -= sizeof(void *);
-		}
-		else
-		{
-			// Just remove control 
-
-			mydelete(myTemp, 0, 1);
-		}
-
-		tx_data = duplicateString(myTemp);		// so can free original below
-
-		Delete(&all_frame_buf[Chan], 0);			// This will invalidate temp
-
-		AGW_AX25_frame_analiz(Chan, FALSE, tx_data);
-
-		put_frame(Chan, tx_data, "", TRUE, FALSE);
-
-		RUHEncode(tx_data->Data, tx_data->Length - 2, Chan);
-
-		freeString(tx_data);
-
-		// Samples are now in DMABuffer = Send first block
-
-		ARDOPSendToCard(Chan, SendSize);
-		tx_status[Chan] = TX_FRAME;
-
-	}
-	else
-		modulator(Chan, tx_bufsize);
-
-	return;
-}
-
-void RX2TX(int snd_ch)
-{
-	if (snd_status[snd_ch] == SND_IDLE)
-	{
-		DoTX(snd_ch);
-	}
-}
-
-// PTT Stuff
-
-int hPTTDevice = 0;
-char PTTPort[80] = "";			// Port for Hardware PTT - may be same as control port.
-int PTTBAUD = 19200;
-int PTTMode = PTTRTS;			// PTT Control Flags.
-
-char PTTOnString[128] = "";
-char PTTOffString[128] = "";
-
-UCHAR PTTOnCmd[64];
-UCHAR PTTOnCmdLen = 0;
-
-UCHAR PTTOffCmd[64];
-UCHAR PTTOffCmdLen = 0;
-
-int pttGPIOPin = 17;			// Default
-int pttGPIOPinR = 17;
-BOOL pttGPIOInvert = FALSE;
-BOOL useGPIO = FALSE;
-BOOL gotGPIO = FALSE;
-
-int HamLibPort = 4532;
-char HamLibHost[32] = "192.168.1.14";
-
-char CM108Addr[80] = "";
-
-int VID = 0;
-int PID = 0;
-
-// CM108 Code
-
-char * CM108Device = NULL;
-
-void DecodeCM108(char * ptr)
-{
-	// Called if Device Name or PTT = Param is CM108
-
-#ifdef WIN32
-
-	// Next Param is VID and PID - 0xd8c:0x8 or Full device name
-	// On Windows device name is very long and difficult to find, so 
-	//	easier to use VID/PID, but allow device in case more than one needed
-
-	char * next;
-	long VID = 0, PID = 0;
-	char product[256] = "Unknown";
-
-	struct hid_device_info *devs, *cur_dev;
-	const char *path_to_open = NULL;
-	hid_device *handle = NULL;
-
-	if (strlen(ptr) > 16)
-		CM108Device = _strdup(ptr);
-	else
-	{
-		VID = strtol(ptr, &next, 0);
-		if (next)
-			PID = strtol(++next, &next, 0);
-
-		// Look for Device
-
-		devs = hid_enumerate((unsigned short)VID, (unsigned short)PID);
-		cur_dev = devs;
-
-		while (cur_dev)
-		{
-			if (cur_dev->product_string)
-				wcstombs(product, cur_dev->product_string, 255);
-			
-			Debugprintf("HID Device %s VID %X PID %X", product, cur_dev->vendor_id, cur_dev->product_id);
-			if (cur_dev->vendor_id == VID && cur_dev->product_id == PID)
-			{
-				path_to_open = cur_dev->path;
-				break;
-			}
-			cur_dev = cur_dev->next;
-		}
-
-		if (path_to_open)
-		{
-			handle = hid_open_path(path_to_open);
-
-			if (handle)
-			{
-				hid_close(handle);
-				CM108Device = _strdup(path_to_open);
-			}
-			else
-			{
-				Debugprintf("Unable to open CM108 device %x %x", VID, PID);
-			}
-		}
-		else
-			Debugprintf("Couldn't find CM108 device %x %x", VID, PID);
-
-		hid_free_enumeration(devs);
-	}
-#else
-
-	// Linux - Next Param HID Device, eg /dev/hidraw0
-
-	CM108Device = _strdup(ptr);
-#endif
-}
-
-char * strlop(char * buf, char delim)
-{
-	// Terminate buf at delim, and return rest of string
-
-	char * ptr = strchr(buf, delim);
-
-	if (ptr == NULL) return NULL;
-
-	*(ptr)++ = 0;
-	return ptr;
-}
-
-void OpenPTTPort()
-{
-	PTTMode &= ~PTTCM108;
-	PTTMode &= ~PTTHAMLIB;
-
-	if (PTTPort[0] && strcmp(PTTPort, "None") != 0)
-	{
-		if (PTTMode == PTTCAT)
-		{
-			// convert config strings from Hex
-
-			char * ptr1 = PTTOffString;
-			UCHAR * ptr2 = PTTOffCmd;
-			char c;
-			int val;
-
-			while (c = *(ptr1++))
-			{
-				val = c - 0x30;
-				if (val > 15) val -= 7;
-				val <<= 4;
-				c = *(ptr1++) - 0x30;
-				if (c > 15) c -= 7;
-				val |= c;
-				*(ptr2++) = val;
-			}
-
-			PTTOffCmdLen = ptr2 - PTTOffCmd;
-
-			ptr1 = PTTOnString;
-			ptr2 = PTTOnCmd;
-
-			while (c = *(ptr1++))
-			{
-				val = c - 0x30;
-				if (val > 15) val -= 7;
-				val <<= 4;
-				c = *(ptr1++) - 0x30;
-				if (c > 15) c -= 7;
-				val |= c;
-				*(ptr2++) = val;
-			}
-
-			PTTOnCmdLen = ptr2 - PTTOnCmd;
-		}
-
-		if (stricmp(PTTPort, "GPIO") == 0)
-		{
-			// Initialise GPIO for PTT if available
-
-#ifdef __ARM_ARCH
-
-			if (gpioInitialise() == 0)
-			{
-				printf("GPIO interface for PTT available\n");
-				gotGPIO = TRUE;
-
-				SetupGPIOPTT();
-			}
-			else
-				printf("Couldn't initialise GPIO interface for PTT\n");
-
-#else
-			printf("GPIO interface for PTT not available on this platform\n");
-#endif
-
-		}
-		else if (stricmp(PTTPort, "CM108") == 0)
-		{
-			DecodeCM108(CM108Addr);
-			PTTMode |= PTTCM108;
-		}
-
-		else if (stricmp(PTTPort, "HAMLIB") == 0)
-		{
-			PTTMode |= PTTHAMLIB;
-			HAMLIBSetPTT(0);			// to open port
-			return;
-		}
-
-		else		//  Not GPIO
-		{
-			hPTTDevice = OpenCOMPort(PTTPort, PTTBAUD, FALSE, FALSE, FALSE, 0);
-		}
-	}
-}
-
-void ClosePTTPort()
-{
-	CloseCOMPort(hPTTDevice);
-	hPTTDevice = 0;
-}
-void CM108_set_ptt(int PTTState)
-{
-	char io[5];
-	hid_device *handle;
-	int n;
-
-	io[0] = 0;
-	io[1] = 0;
-	io[2] = 1 << (3 - 1);
-	io[3] = PTTState << (3 - 1);
-	io[4] = 0;
-
-	if (CM108Device == NULL)
-		return;
-
-#ifdef WIN32
-	handle = hid_open_path(CM108Device);
-
-	if (!handle) {
-		printf("unable to open device\n");
-		return;
-	}
-
-	n = hid_write(handle, io, 5);
-	if (n < 0)
-	{
-		printf("Unable to write()\n");
-		printf("Error: %ls\n", hid_error(handle));
-	}
-
-	hid_close(handle);
-
-#else
-
-	int fd;
-
-	fd = open(CM108Device, O_WRONLY);
-
-	if (fd == -1)
-	{
-		printf("Could not open %s for write, errno=%d\n", CM108Device, errno);
-		return;
-	}
-
-	io[0] = 0;
-	io[1] = 0;
-	io[2] = 1 << (3 - 1);
-	io[3] = PTTState << (3 - 1);
-	io[4] = 0;
-
-	n = write(fd, io, 5);
-	if (n != 5)
-	{
-		printf("Write to %s failed, n=%d, errno=%d\n", CM108Device, n, errno);
-	}
-
-	close(fd);
-#endif
-	return;
-
-}
-
-
-
-void RadioPTT(int snd_ch, BOOL PTTState)
-{
-	snd_status[snd_ch] = PTTState; // SND_IDLE = 0 SND_TX = 1 
-
-#ifdef __ARM_ARCH
-	if (useGPIO)
-	{
-		if (DualPTT && modemtoSoundLR[snd_ch] == 1)
-			gpioWrite(pttGPIOPinR, (pttGPIOInvert ? (1 - PTTState) : (PTTState)));
-		else
-			gpioWrite(pttGPIOPin, (pttGPIOInvert ? (1 - PTTState) : (PTTState)));
-
-		return;
-	}
-
-#endif
-
-	if ((PTTMode & PTTCM108))
-	{
-		CM108_set_ptt(PTTState);
-		return;
-	}
-	
-	if ((PTTMode & PTTHAMLIB))
-	{
-		HAMLIBSetPTT(PTTState);
-		return;
-	}
-	if (hPTTDevice == 0)
-		return;
-
-	if ((PTTMode & PTTCAT))
-	{
-		if (PTTState)
-			WriteCOMBlock(hPTTDevice, PTTOnCmd, PTTOnCmdLen);
-		else
-			WriteCOMBlock(hPTTDevice, PTTOffCmd, PTTOffCmdLen);
-
-		return;
-	}
-
-	if (DualPTT && modemtoSoundLR[snd_ch] == 1)		// use DTR
-	{
-		if (PTTState)
-			COMSetDTR(hPTTDevice);
-		else
-			COMClearDTR(hPTTDevice);
-	}
-	else
-	{
-		if ((PTTMode & PTTRTS))
-		{
-			if (PTTState)
-				COMSetRTS(hPTTDevice);
-			else
-				COMClearRTS(hPTTDevice);
-		}
-	}
-
-}
-
-char ShortDT[] = "HH:MM:SS";
-
-char * ShortDateTime()
-{
-	struct tm * tm;
-	time_t NOW = time(NULL);
-
-	tm = gmtime(&NOW);
-
-	sprintf(ShortDT, "%02d:%02d:%02d", tm->tm_hour, tm->tm_min, tm->tm_sec);
-	return ShortDT;
-}
-
-
-// Reed Solomon Stuff
-
-
-int NPAR = -1;	// Number of Parity Bytes - used in RS Code
-
-int xMaxErrors = 0;
-
-int RSEncode(UCHAR * bytToRS, UCHAR * RSBytes, int DataLen, int RSLen)
-{
-	// This just returns the Parity Bytes. I don't see the point
-	// in copying the message about
-
-	unsigned char Padded[256];		// The padded Data
-
-	int Length = DataLen + RSLen;	// Final Length of packet
-	int PadLength = 255 - Length;	// Padding bytes needed for shortened RS codes
-
-	//	subroutine to do the RS encode. For full length and shortend RS codes up to 8 bit symbols (mm = 8)
-
-	if (NPAR != RSLen)		// Changed RS Len, so recalc constants;
-	{
-		NPAR = RSLen;
-		xMaxErrors = NPAR / 2;
-		initialize_ecc();
-	}
-
-	// Copy the supplied data to end of data array.
-
-	memset(Padded, 0, PadLength);
-	memcpy(&Padded[PadLength], bytToRS, DataLen);
-
-	encode_data(Padded, 255 - RSLen, RSBytes);
-
-	return RSLen;
-}
-
-//	Main RS decode function
-
-extern int index_of[];
-extern int recd[];
-extern int Corrected[256];
-extern int tt;		//  number of errors that can be corrected 
-extern int kk;		// Info Symbols
-
-extern BOOL blnErrorsCorrected;
-
-
-BOOL RSDecode(UCHAR * bytRcv, int Length, int CheckLen, BOOL * blnRSOK)
-{
-
-
-	// Using a modified version of Henry Minsky's code
-
-	//Copyright Henry Minsky (hqm@alum.mit.edu) 1991-2009
-
-	// Rick's Implementation processes the byte array in reverse. and also 
-	//	has the check bytes in the opposite order. I've modified the encoder
-	//	to allow for this, but so far haven't found a way to mske the decoder
-	//	work, so I have to reverse the data and checksum to decode G8BPQ Nov 2015
-
-	//	returns TRUE if was ok or correction succeeded, FALSE if correction impossible
-
-	UCHAR intTemp[256];				// WOrk Area to pass to Decoder		
-	int i;
-	UCHAR * ptr2 = intTemp;
-	UCHAR * ptr1 = &bytRcv[Length - CheckLen - 1]; // Last Byte of Data
-
-	int DataLen = Length - CheckLen;
-	int PadLength = 255 - Length;		// Padding bytes needed for shortened RS codes
-
-	*blnRSOK = FALSE;
-
-	if (Length > 255 || Length < (1 + CheckLen))		//Too long or too short 
-		return FALSE;
-
-	if (NPAR != CheckLen)		// Changed RS Len, so recalc constants;
-	{
-		NPAR = CheckLen;
-		xMaxErrors = NPAR / 2;
-
-		initialize_ecc();
-	}
-
-
-	//	We reverse the data while zero padding it to speed things up
-
-	//	We Need (Data Reversed) (Zero Padding) (Checkbytes Reversed)
-
-	// Reverse Data
-
-	for (i = 0; i < DataLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	//	Clear padding
-
-	memset(ptr2, 0, PadLength);
-
-	ptr2 += PadLength;
-
-	// Error Bits
-
-	ptr1 = &bytRcv[Length - 1];			// End of check bytes
-
-	for (i = 0; i < CheckLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	decode_data(intTemp, 255);
-
-	// check if syndrome is all zeros 
-
-	if (check_syndrome() == 0)
-	{
-		// RS ok, so no need to correct
-
-		*blnRSOK = TRUE;
-		return TRUE;		// No Need to Correct
-	}
-
-	if (correct_errors_erasures(intTemp, 255, 0, 0) == 0) // Dont support erasures at the momnet
-
-		// Uncorrectable
-
-		return FALSE;
-
-	// Data has been corrected, so need to reverse again
-
-	ptr1 = &intTemp[DataLen - 1];
-	ptr2 = bytRcv; // Last Byte of Data
-
-	for (i = 0; i < DataLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	// ?? Do we need to return the check bytes ??
-
-	// Yes, so we can redo RS Check on supposedly connected frame
-
-	ptr1 = &intTemp[254];	// End of Check Bytes
-
-	for (i = 0; i < CheckLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	return TRUE;
-}
-
-extern TStringList detect_list[5];
-extern TStringList detect_list_c[5];
-
-void ProcessPktFrame(int snd_ch, UCHAR * Data, int frameLen)
-{
-	string * pkt = newString();
-
-	stringAdd(pkt, Data, frameLen + 2);			// 2 for crc (not actually there)
-
-	analiz_frame(snd_ch, pkt, "ARDOP", 1);
-
-}
diff --git a/SMMain-HPLaptop.c b/SMMain-HPLaptop.c
deleted file mode 100644
index 8daaf17..0000000
--- a/SMMain-HPLaptop.c
+++ /dev/null
@@ -1,1381 +0,0 @@
-/*
-Copyright (C) 2019-2020 Andrei Kopanchuk UZ7HO
-
-This file is part of QtSoundModem
-
-QtSoundModem is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-QtSoundModem is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with QtSoundModem.  If not, see http://www.gnu.org/licenses
-
-*/
-
-// UZ7HO Soundmodem Port by John Wiseman G8BPQ
-
-#include "UZ7HOStuff.h"
-#include "fftw3.h"
-#include <time.h>
-#include "ecc.h"				// RS Constants
-#include "hidapi.h"
-#include <fcntl.h>
-#include <errno.h>
-
-BOOL KISSServ;
-int KISSPort;
-
-BOOL AGWServ;
-int AGWPort;
-
-int Number = 0;				// Number waiting to be sent
-
-int SoundIsPlaying = 0;
-int UDPSoundIsPlaying = 0;
-int Capturing = 0;
-
-extern unsigned short buffer[2][1200];
-extern int SoundMode;
-extern int needRSID[4];
-
-extern short * DMABuffer;
-
-unsigned short * SendtoCard(unsigned short * buf, int n);
-short * SoundInit();
-void DoTX(int Chan);
-void UDPPollReceivedSamples();
-
-
-extern int SampleNo;
-
-extern int pnt_change[5];				// Freq Changed Flag
-
-// fftw library interface
-
-
-fftwf_complex *in, *out;
-fftwf_plan p;
-
-#define N 2048
-
-void initfft()
-{
-	in = (fftwf_complex*)fftwf_malloc(sizeof(fftwf_complex) * N);
-	out = (fftwf_complex*)fftwf_malloc(sizeof(fftwf_complex) * N);
-	p = fftwf_plan_dft_1d(N, in, out, FFTW_FORWARD, FFTW_ESTIMATE);
-}
-
-void dofft(short * inp, float * outr, float * outi)
-{
-	int i;
-	
-	fftwf_complex * fft = in;
-
-	for (i = 0; i < N; i++)
-	{
-		fft[0][0] = inp[0] * 1.0f;
-		fft[0][1] = 0;
-		fft++;
-		inp++;
-	}
-
-	fftwf_execute(p); 
-
-	fft = out;
-
-	for (i = 0; i < N; i++)
-	{
-		outr[0] = fft[0][0];
-		outi[0] = fft[0][1];
-		fft++;
-		outi++;
-		outr++;
-	}
-}
-
-void freefft()
-{
-	fftwf_destroy_plan(p);
-	fftwf_free(in);
-	fftwf_free(out);
-}
-
-int nonGUIMode = 0;
-
-void soundMain()
-{
-	// non platform specific initialisation
-
-	platformInit();
-
-	// initialise fft library
-
-	RsCreate();				// RS code for MPSK
-
-	detector_init();
-	KISS_init();
-	ax25_init();
-	init_raduga();			// Set up waterfall colour table
-
-	initfft();
-
-	if (nonGUIMode)
-	{
-		Firstwaterfall = 0;
-		Secondwaterfall = 0;
-	}
-
-	OpenPTTPort();
-}
-
-
-void SampleSink(int LR, short Sample)
-{
-	// This version is passed samples one at a time, as we don't have
-	//	enough RAM in embedded systems to hold a full audio frame
-
-	// LR - 1 == Right Chan
-
-#ifdef TEENSY	
-		int work = Sample;
-		DMABuffer[Number++] = (work + 32768) >> 4; // 12 bit left justify
-#else
-	if (SCO)			// Single Channel Output - same to both L and R
-	{
-		DMABuffer[2 * Number] = Sample;
-		DMABuffer[1 + 2 * Number] = Sample;
-
-	}
-	else
-	{
-		if (LR)				// Right
-		{
-			DMABuffer[1 + 2 * Number] = Sample;
-			DMABuffer[2 * Number] = 0;
-		}
-		else
-		{
-			DMABuffer[2 * Number] = Sample;
-			DMABuffer[1 + 2 * Number] = 0;
-		}
-	}
-	Number++;
-#endif
-		if (Number >= SendSize)
-		{
-			// send this buffer to sound interface
-
-			DMABuffer = SendtoCard(DMABuffer, SendSize);
-			Number = 0;
-		}
-	
-
-//	Last120[Last120Put++] = Sample;
-
-//	if (Last120Put == (intN + 1))
-//		Last120Put = 0;
-
-	SampleNo++;
-}
-
-
-void Flush()
-{
-	SoundFlush(Number);
-}
-
-int ipow(int base, int exp)
-{
-	int result = 1;
-	while (exp)
-	{
-		if (exp & 1)
-			result *= base;
-		exp >>= 1;
-		base *= base;
-	}
-
-	return result;
-}
-
-int NumberOfBitsNeeded(int PowerOfTwo)
-{
-	int i;
-
-	for (i = 0; i <= 16; i++)
-	{
-		if ((PowerOfTwo & ipow(2, i)) != 0)
-			return i;
-
-	}
-	return 0;
-}
-
-
-int ReverseBits(int Index, int NumBits)
-{
-	int i, Rev = 0;
-
-	for (i = 0; i < NumBits; i++)
-	{
-		Rev = (Rev * 2) | (Index & 1);
-		Index = Index / 2;
-	}
-
-	return Rev;
-}
-
-
-void FourierTransform(int NumSamples, short * RealIn, float * RealOut, float * ImagOut, int InverseTransform)
-{
-	float AngleNumerator;
-	unsigned char NumBits;
-
-	int i, j, K, n, BlockSize, BlockEnd;
-	float DeltaAngle, DeltaAr;
-	float Alpha, Beta;
-	float TR, TI, AR, AI;
-
-	if (InverseTransform)
-		AngleNumerator = -2.0f * M_PI;
-	else
-		AngleNumerator = 2.0f * M_PI;
-
-	NumBits = NumberOfBitsNeeded(NumSamples);
-
-	for (i = 0; i < NumSamples; i++)
-	{
-		j = ReverseBits(i, NumBits);
-		RealOut[j] = RealIn[i];
-		ImagOut[j] = 0.0f; // Not using i in ImageIn[i];
-	}
-
-	BlockEnd = 1;
-	BlockSize = 2;
-
-	while (BlockSize <= NumSamples)
-	{
-		DeltaAngle = AngleNumerator / BlockSize;
-		Alpha = sinf(0.5f * DeltaAngle);
-		Alpha = 2.0f * Alpha * Alpha;
-		Beta = sinf(DeltaAngle);
-
-		i = 0;
-
-		while (i < NumSamples)
-		{
-			AR = 1.0f;
-			AI = 0.0f;
-
-			j = i;
-
-			for (n = 0; n < BlockEnd; n++)
-			{
-				K = j + BlockEnd;
-				TR = AR * RealOut[K] - AI * ImagOut[K];
-				TI = AI * RealOut[K] + AR * ImagOut[K];
-				RealOut[K] = RealOut[j] - TR;
-				ImagOut[K] = ImagOut[j] - TI;
-				RealOut[j] = RealOut[j] + TR;
-				ImagOut[j] = ImagOut[j] + TI;
-				DeltaAr = Alpha * AR + Beta * AI;
-				AI = AI - (Alpha * AI - Beta * AR);
-				AR = AR - DeltaAr;
-				j = j + 1;
-			}
-			i = i + BlockSize;
-		}
-		BlockEnd = BlockSize;
-		BlockSize = BlockSize * 2;
-	}
-
-	if (InverseTransform)
-	{
-		//	Normalize the resulting time samples...
-
-		for (i = 0; i < NumSamples; i++)
-		{
-			RealOut[i] = RealOut[i] / NumSamples;
-			ImagOut[i] = ImagOut[i] / NumSamples;
-		}
-	}
-}
-
-
-
-int LastBusyCheck = 0;
-
-extern UCHAR CurrentLevel;
-
-#ifdef PLOTSPECTRUM		
-float dblMagSpectrum[206];
-float dblMaxScale = 0.0f;
-extern UCHAR Pixels[4096];
-extern UCHAR * pixelPointer;
-#endif
-
-extern int blnBusyStatus;
-BusyDet = 0;
-
-#define PLOTWATERFALL
-
-int WaterfallActive = 1;
-int SpectrumActive;
-
-/*
-
-void UpdateBusyDetector(short * bytNewSamples)
-{
-	float dblReF[1024];
-	float dblImF[1024];
-	float dblMag[206];
-#ifdef PLOTSPECTRUM
-	float dblMagMax = 0.0000000001f;
-	float dblMagMin = 10000000000.0f;
-#endif
-	UCHAR Waterfall[256];			// Colour index values to send to GUI
-	int clrTLC = Lime;				// Default Bandwidth lines on waterfall
-
-	static BOOL blnLastBusyStatus;
-
-	float dblMagAvg = 0;
-	int intTuneLineLow, intTuneLineHi, intDelta;
-	int i;
-
-	//	if (State != SearchingForLeader)
-	//		return;						// only when looking for leader
-
-	if (Now - LastBusyCheck < 100)
-		return;
-
-	LastBusyCheck = Now;
-
-	FourierTransform(1024, bytNewSamples, &dblReF[0], &dblImF[0], FALSE);
-
-	for (i = 0; i < 206; i++)
-	{
-		//	starting at ~300 Hz to ~2700 Hz Which puts the center of the signal in the center of the window (~1500Hz)
-
-		dblMag[i] = powf(dblReF[i + 25], 2) + powf(dblImF[i + 25], 2);	 // first pass 
-		dblMagAvg += dblMag[i];
-#ifdef PLOTSPECTRUM		
-		dblMagSpectrum[i] = 0.2f * dblMag[i] + 0.8f * dblMagSpectrum[i];
-		dblMagMax = max(dblMagMax, dblMagSpectrum[i]);
-		dblMagMin = min(dblMagMin, dblMagSpectrum[i]);
-#endif
-	}
-
-	//	LookforPacket(dblMag, dblMagAvg, 206, &dblReF[25], &dblImF[25]);
-	//	packet_process_samples(bytNewSamples, 1200);
-
-	intDelta = roundf(500 / 2) + 50 / 11.719f;
-
-	intTuneLineLow = max((103 - intDelta), 3);
-	intTuneLineHi = min((103 + intDelta), 203);
-
-//	if (ProtocolState == DISC)		// ' Only process busy when in DISC state
-	{
-	//	blnBusyStatus = BusyDetect3(dblMag, intTuneLineLow, intTuneLineHi);
-
-		if (blnBusyStatus && !blnLastBusyStatus)
-		{
-//			QueueCommandToHost("BUSY TRUE");
-//			newStatus = TRUE;				// report to PTC
-
-			if (!WaterfallActive && !SpectrumActive)
-			{
-				UCHAR Msg[2];
-
-//				Msg[0] = blnBusyStatus;
-//				SendtoGUI('B', Msg, 1);
-			}
-		}
-		//    stcStatus.Text = "TRUE"
-			//    queTNCStatus.Enqueue(stcStatus)
-			//    'Debug.WriteLine("BUSY TRUE @ " & Format(DateTime.UtcNow, "HH:mm:ss"))
-
-		else if (blnLastBusyStatus && !blnBusyStatus)
-		{
-//			QueueCommandToHost("BUSY FALSE");
-//			newStatus = TRUE;				// report to PTC
-
-			if (!WaterfallActive && !SpectrumActive)
-			{
-				UCHAR Msg[2];
-
-				Msg[0] = blnBusyStatus;
-//				SendtoGUI('B', Msg, 1);
-			}
-		}
-		//    stcStatus.Text = "FALSE"
-		//    queTNCStatus.Enqueue(stcStatus)
-		//    'Debug.WriteLine("BUSY FALSE @ " & Format(DateTime.UtcNow, "HH:mm:ss"))
-
-		blnLastBusyStatus = blnBusyStatus;
-	}
-
-	if (BusyDet == 0)
-		clrTLC = Goldenrod;
-	else if (blnBusyStatus)
-		clrTLC = Fuchsia;
-
-	// At the moment we only get here what seaching for leader,
-	// but if we want to plot spectrum we should call
-	// it always
-
-
-
-	if (WaterfallActive)
-	{
-#ifdef PLOTWATERFALL
-		dblMagAvg = log10f(dblMagAvg / 5000.0f);
-
-		for (i = 0; i < 206; i++)
-		{
-			// The following provides some AGC over the waterfall to compensate for avg input level.
-
-			float y1 = (0.25f + 2.5f / dblMagAvg) * log10f(0.01 + dblMag[i]);
-			int objColor;
-
-			// Set the pixel color based on the intensity (log) of the spectral line
-			if (y1 > 6.5)
-				objColor = Orange; // Strongest spectral line 
-			else if (y1 > 6)
-				objColor = Khaki;
-			else if (y1 > 5.5)
-				objColor = Cyan;
-			else if (y1 > 5)
-				objColor = DeepSkyBlue;
-			else if (y1 > 4.5)
-				objColor = RoyalBlue;
-			else if (y1 > 4)
-				objColor = Navy;
-			else
-				objColor = Black;
-
-			if (i == 102)
-				Waterfall[i] = Tomato;  // 1500 Hz line (center)
-			else if (i == intTuneLineLow || i == intTuneLineLow - 1 || i == intTuneLineHi || i == intTuneLineHi + 1)
-				Waterfall[i] = clrTLC;
-			else
-				Waterfall[i] = objColor; // ' Else plot the pixel as received
-		}
-
-		// Send Signal level and Busy indicator to save extra packets
-
-		Waterfall[206] = CurrentLevel;
-		Waterfall[207] = blnBusyStatus;
-
-		doWaterfall(Waterfall);
-#endif
-	}
-	else if (SpectrumActive)
-	{
-#ifdef PLOTSPECTRUM
-		// This performs an auto scaling mechansim with fast attack and slow release
-		if (dblMagMin / dblMagMax < 0.0001) // more than 10000:1 difference Max:Min
-			dblMaxScale = max(dblMagMax, dblMaxScale * 0.9f);
-		else
-			dblMaxScale = max(10000 * dblMagMin, dblMagMax);
-
-//		clearDisplay();
-
-		for (i = 0; i < 206; i++)
-		{
-			// The following provides some AGC over the spectrum to compensate for avg input level.
-
-			float y1 = -0.25f * (SpectrumHeight - 1) *  log10f((max(dblMagSpectrum[i], dblMaxScale / 10000)) / dblMaxScale); // ' range should be 0 to bmpSpectrumHeight -1
-			int objColor = Yellow;
-
-			Waterfall[i] = round(y1);
-		}
-
-		// Send Signal level and Busy indicator to save extra packets
-
-		Waterfall[206] = CurrentLevel;
-		Waterfall[207] = blnBusyStatus;
-		Waterfall[208] = intTuneLineLow;
-		Waterfall[209] = intTuneLineHi;
-
-//		SendtoGUI('X', Waterfall, 210);
-#endif
-	}
-}
-
-*/
-
-extern short rawSamples[2400];	// Get Frame Type need 2400 and we may add 1200
-int rawSamplesLength = 0;
-extern int maxrawSamplesLength;
-
-void ProcessNewSamples(short * Samples, int nSamples)
-{
-	if (SoundIsPlaying == FALSE && UDPSoundIsPlaying == FALSE)
-		BufferFull(Samples, nSamples);
-};
-
-void doCalib(int Chan, int Act)
-{
-	if (Chan == 0 && calib_mode[1])
-		return;						
-	
-	if (Chan == 1 && calib_mode[0])
-		return;
-
-	calib_mode[Chan] = Act;
-
-	if (Act == 0)
-	{
-		tx_status[Chan] = TX_SILENCE;		// Stop TX
-		Flush();
-		RadioPTT(Chan, 0);
-		Debugprintf("Stop Calib");
-	}
-}
-
-int Freq_Change(int Chan, int Freq)
-{
-	int low, high;
-
-	low = round(rx_shift[1] / 2 + RCVR[Chan] * rcvr_offset[Chan] + 1);
-	high = round(RX_Samplerate / 2 - (rx_shift[Chan] / 2 + RCVR[Chan] * rcvr_offset[Chan]));
-
-	if (Freq < low)
-		return rx_freq[Chan];				// Dont allow change
-
-	if (Freq > high)
-		return rx_freq[Chan];				// Dont allow change
-
-	rx_freq[Chan] = Freq;
-	tx_freq[Chan] = Freq;
-
-	pnt_change[Chan] = TRUE;
-	wf_pointer(soundChannel[Chan]);
-
-	return Freq;
-}
-
-void MainLoop()
-{
-	// Called by background thread every 10 ms (maybe)
-
-	// Actually we may have two cards
-	
-	// Original only allowed one channel per card.
-	// I think we should be able to run more, ie two or more
-	// modems on same soundcard channel
-	
-	// So All the soundcard stuff will need to be generalised
-
-	if (UDPServ)
-		UDPPollReceivedSamples();
-
-	if (SoundMode == 3)
-		UDPPollReceivedSamples();
-	else
-		PollReceivedSamples();
-
-
-	if (modem_mode[0] == MODE_ARDOP)
-	{
-		chk_dcd1(0, 512);
-	}
-
-	DoTX(0);
-	DoTX(1);
-	DoTX(2);
-	DoTX(3);
-
-}
-
-int ARDOPSendToCard(int Chan, int Len)
-{
-	// Send Next Block of samples to the soundcard
-
-	short * in = &ARDOPTXBuffer[Chan][ARDOPTXPtr[Chan]];		// Enough to hold whole frame of samples
-	short * out = DMABuffer;
-
-	int LR = modemtoSoundLR[Chan];
-
-	int i;
-
-	for (i = 0; i < Len; i++)
-	{
-		if (SCO)			// Single Channel Output - same to both L and R
-		{
-			*out++ = *in;
-			*out++ = *in++;
-		}
-		else
-		{
-			if (LR)				// Right
-			{
-				*out++ = 0;
-				*out++ = *in++;
-			}
-			else
-			{
-				*out++ = *in++;
-				*out++ = 0;
-			}
-		}
-	}
-	DMABuffer = SendtoCard(DMABuffer, Len);
-
-	ARDOPTXPtr[Chan] += Len;
-
-	// See if end of buffer
-
-	if (ARDOPTXPtr[Chan] > ARDOPTXLen[Chan])
-		return 1;
-
-	return 0;
-}
-void DoTX(int Chan)
-{
-	// This kicks off a send sequence or calibrate
-
-//	printtick("dotx");
-
-	if (calib_mode[Chan])
-	{
-		// Maybe new calib or continuation
-
-		if (pnt_change[Chan])
-		{
-			make_core_BPF(Chan, rx_freq[Chan], bpf[Chan]);
-			make_core_TXBPF(Chan, tx_freq[Chan], txbpf[Chan]);
-			pnt_change[Chan] = FALSE;
-		}
-		
-		// Note this may block in SendtoCard
-
-		modulator(Chan, tx_bufsize);
-		return;
-	}
-
-	// I think we have to detect NO_DATA here and drop PTT and return to SILENCE
-
-	if (tx_status[Chan] == TX_NO_DATA)
-	{
-		Flush();
-		Debugprintf("TX Complete");
-		RadioPTT(0, 0);
-		tx_status[Chan] = TX_SILENCE;
-
-		// We should now send any ackmode acks as the channel is now free for dest to reply
-
-		sendAckModeAcks(Chan);
-	}
-
-	if (tx_status[Chan] != TX_SILENCE)
-	{
-		// Continue the send
-
-		if (modem_mode[Chan] == MODE_ARDOP)
-		{
-//			if (SeeIfCardBusy())
-//				return 0;
-
-			if (ARDOPSendToCard(Chan, SendSize) == 1)
-			{
-				// End of TX
-
-				Number = 0;
-				Flush();
-
-				// See if more to send. If so, don't drop PTT
-
-				if (all_frame_buf[Chan].Count)
-				{
-					SoundIsPlaying = TRUE;
-					Number = 0;
-
-					Debugprintf("TX Continuing");
-
-					string * myTemp = Strings(&all_frame_buf[Chan], 0);			// get message
-					string * tx_data;
-
-					if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-					{
-						// Save copy then copy data up 3 bytes
-
-						Add(&KISS_acked[Chan], duplicateString(myTemp));
-
-						mydelete(myTemp, 0, 3);
-						myTemp->Length -= sizeof(void *);
-					}
-					else
-					{
-						// Just remove control 
-
-						mydelete(myTemp, 0, 1);
-					}
-
-					tx_data = duplicateString(myTemp);		// so can free original below
-
-					Delete(&all_frame_buf[Chan], 0);			// This will invalidate temp
-
-					AGW_AX25_frame_analiz(Chan, FALSE, tx_data);
-
-					put_frame(Chan, tx_data, "", TRUE, FALSE);
-
-					PktARDOPEncode(tx_data->Data, tx_data->Length - 2, Chan);
-
-					freeString(tx_data);
-
-					// Samples are now in DMABuffer = Send first block
-
-					ARDOPSendToCard(Chan, SendSize);
-					tx_status[Chan] = TX_FRAME;
-					return;
-				}
-
-				Debugprintf("TX Complete");
-				RadioPTT(0, 0);
-				tx_status[Chan] = TX_SILENCE;
-
-				// We should now send any ackmode acks as the channel is now free for dest to reply
-			}
-
-			return;
-		}
-
-		modulator(Chan, tx_bufsize); 
-		return;
-	}
-
-	if (SoundIsPlaying || UDPSoundIsPlaying)
-		return;
-
-	// Not doing anything so see if we have anything new to send
-
-	// See if frequency has changed
-
-	if (pnt_change[Chan])
-	{
-		make_core_BPF(Chan, rx_freq[Chan], bpf[Chan]);
-		make_core_TXBPF(Chan, tx_freq[Chan], txbpf[Chan]);
-		pnt_change[Chan] = FALSE;
-	}
-
-	// See if we need an RSID
-
-	if (needRSID[Chan])
-	{
-		needRSID[Chan] = 0;
-
-		// Note this may block in SampleSink
-
-		Debugprintf("Sending RSID");
-		sendRSID(Chan, all_frame_buf[Chan].Count == 0);
-		return;
-	}
-
-	if (all_frame_buf[Chan].Count == 0)
-		return;
-
-	// Start a new send. modulator should handle TXD etc
-
-	Debugprintf("TX Start");
-	SampleNo = 0;
-
-	SoundIsPlaying = TRUE;
-	RadioPTT(Chan, 1);
-	Number = 0;
-
-	if (modem_mode[Chan] == MODE_ARDOP)
-	{
-		// I think ARDOP will have to generate a whole frame of samples
-		// then send them out a bit at a time to avoid stopping here for
-		// possibly 10's of seconds
-
-		// Can do this here as unlike normal ardop we don't need to run on Teensy
-		// to 12000 sample rate we need either 24K or 48K per second, depending on
-		// where we do the stereo mux. 
-
-		// Slowest rate is 50 baud, so a 255 byte packet would take about a minute
-		// allowing for RS overhead. Not really realistic put perhaps should be possible.
-		// RAM isn't an issue so maybe allocate 2 MB. 
-
-		// ?? Should we allow two ARDOP modems - could make sense if we can run sound
-		// card channels independently
-
-		string * myTemp = Strings(&all_frame_buf[Chan], 0);			// get message
-		string * tx_data;
-
-		if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-		{
-			// Save copy then copy data up 3 bytes
-
-			Add(&KISS_acked[Chan], duplicateString(myTemp));
-
-			mydelete(myTemp, 0, 3);
-			myTemp->Length -= sizeof(void *);
-		}
-		else
-		{
-			// Just remove control 
-
-			mydelete(myTemp, 0, 1);
-		}
-
-		tx_data = duplicateString(myTemp);		// so can free original below
-
-		Delete(&all_frame_buf[Chan], 0);			// This will invalidate temp
-
-		AGW_AX25_frame_analiz(Chan, FALSE, tx_data);
-
-		put_frame(Chan, tx_data, "", TRUE, FALSE);
-
-		PktARDOPEncode(tx_data->Data, tx_data->Length - 2, Chan);
-
-		freeString(tx_data);
-
-		// Samples are now in DMABuffer = Send first block
-
-		ARDOPSendToCard(Chan, SendSize);
-		tx_status[Chan] = TX_FRAME;
-
-	}
-	else
-		modulator(Chan, tx_bufsize);
-
-	return;
-}
-
-void stoptx(int snd_ch)
-{
-	Flush();
-	Debugprintf("TX Complete");
-	RadioPTT(snd_ch, 0);
-	tx_status[snd_ch] = TX_SILENCE;
-
-	snd_status[snd_ch] = SND_IDLE;
-}
-
-void RX2TX(int snd_ch)
-{
-	if (snd_status[snd_ch] == SND_IDLE)
-	{
-		DoTX(snd_ch);
-	}
-}
-
-// PTT Stuff
-
-int hPTTDevice = 0;
-char PTTPort[80] = "";			// Port for Hardware PTT - may be same as control port.
-int PTTBAUD = 19200;
-int PTTMode = PTTRTS;			// PTT Control Flags.
-
-char PTTOnString[128] = "";
-char PTTOffString[128] = "";
-
-UCHAR PTTOnCmd[64];
-UCHAR PTTOnCmdLen = 0;
-
-UCHAR PTTOffCmd[64];
-UCHAR PTTOffCmdLen = 0;
-
-int pttGPIOPin = 17;			// Default
-int pttGPIOPinR = 17;
-BOOL pttGPIOInvert = FALSE;
-BOOL useGPIO = FALSE;
-BOOL gotGPIO = FALSE;
-
-int HamLibPort = 4532;
-char HamLibHost[32] = "192.168.1.14";
-
-char CM108Addr[80] = "";
-
-int VID = 0;
-int PID = 0;
-
-// CM108 Code
-
-char * CM108Device = NULL;
-
-void DecodeCM108(char * ptr)
-{
-	// Called if Device Name or PTT = Param is CM108
-
-#ifdef WIN32
-
-	// Next Param is VID and PID - 0xd8c:0x8 or Full device name
-	// On Windows device name is very long and difficult to find, so 
-	//	easier to use VID/PID, but allow device in case more than one needed
-
-	char * next;
-	long VID = 0, PID = 0;
-	char product[256] = "Unknown";
-
-	struct hid_device_info *devs, *cur_dev;
-	const char *path_to_open = NULL;
-	hid_device *handle = NULL;
-
-	if (strlen(ptr) > 16)
-		CM108Device = _strdup(ptr);
-	else
-	{
-		VID = strtol(ptr, &next, 0);
-		if (next)
-			PID = strtol(++next, &next, 0);
-
-		// Look for Device
-
-		devs = hid_enumerate((unsigned short)VID, (unsigned short)PID);
-		cur_dev = devs;
-
-		while (cur_dev)
-		{
-			if (cur_dev->product_string)
-				wcstombs(product, cur_dev->product_string, 255);
-			
-			Debugprintf("HID Device %s VID %X PID %X", product, cur_dev->vendor_id, cur_dev->product_id);
-			if (cur_dev->vendor_id == VID && cur_dev->product_id == PID)
-			{
-				path_to_open = cur_dev->path;
-				break;
-			}
-			cur_dev = cur_dev->next;
-		}
-
-		if (path_to_open)
-		{
-			handle = hid_open_path(path_to_open);
-
-			if (handle)
-			{
-				hid_close(handle);
-				CM108Device = _strdup(path_to_open);
-			}
-			else
-			{
-				Debugprintf("Unable to open CM108 device %x %x", VID, PID);
-			}
-		}
-		else
-			Debugprintf("Couldn't find CM108 device %x %x", VID, PID);
-
-		hid_free_enumeration(devs);
-	}
-#else
-
-	// Linux - Next Param HID Device, eg /dev/hidraw0
-
-	CM108Device = _strdup(ptr);
-#endif
-}
-
-char * strlop(char * buf, char delim)
-{
-	// Terminate buf at delim, and return rest of string
-
-	char * ptr = strchr(buf, delim);
-
-	if (ptr == NULL) return NULL;
-
-	*(ptr)++ = 0;
-	return ptr;
-}
-
-void OpenPTTPort()
-{
-	PTTMode &= ~PTTCM108;
-	PTTMode &= ~PTTHAMLIB;
-
-	if (PTTPort[0] && strcmp(PTTPort, "None") != 0)
-	{
-		if (PTTMode == PTTCAT)
-		{
-			// convert config strings from Hex
-
-			char * ptr1 = PTTOffString;
-			UCHAR * ptr2 = PTTOffCmd;
-			char c;
-			int val;
-
-			while (c = *(ptr1++))
-			{
-				val = c - 0x30;
-				if (val > 15) val -= 7;
-				val <<= 4;
-				c = *(ptr1++) - 0x30;
-				if (c > 15) c -= 7;
-				val |= c;
-				*(ptr2++) = val;
-			}
-
-			PTTOffCmdLen = ptr2 - PTTOffCmd;
-
-			ptr1 = PTTOnString;
-			ptr2 = PTTOnCmd;
-
-			while (c = *(ptr1++))
-			{
-				val = c - 0x30;
-				if (val > 15) val -= 7;
-				val <<= 4;
-				c = *(ptr1++) - 0x30;
-				if (c > 15) c -= 7;
-				val |= c;
-				*(ptr2++) = val;
-			}
-
-			PTTOnCmdLen = ptr2 - PTTOnCmd;
-		}
-
-		if (stricmp(PTTPort, "GPIO") == 0)
-		{
-			// Initialise GPIO for PTT if available
-
-#ifdef __ARM_ARCH
-
-			if (gpioInitialise() == 0)
-			{
-				printf("GPIO interface for PTT available\n");
-				gotGPIO = TRUE;
-
-				SetupGPIOPTT();
-			}
-			else
-				printf("Couldn't initialise GPIO interface for PTT\n");
-
-#else
-			printf("GPIO interface for PTT not available on this platform\n");
-#endif
-
-		}
-		else if (stricmp(PTTPort, "CM108") == 0)
-		{
-			DecodeCM108(CM108Addr);
-			PTTMode |= PTTCM108;
-		}
-
-		else if (stricmp(PTTPort, "HAMLIB") == 0)
-		{
-			PTTMode |= PTTHAMLIB;
-			HAMLIBSetPTT(0);			// to open port
-			return;
-		}
-
-		else		//  Not GPIO
-		{
-			hPTTDevice = OpenCOMPort(PTTPort, PTTBAUD, FALSE, FALSE, FALSE, 0);
-		}
-	}
-}
-
-void ClosePTTPort()
-{
-	CloseCOMPort(hPTTDevice);
-	hPTTDevice = 0;
-}
-void CM108_set_ptt(int PTTState)
-{
-	char io[5];
-	hid_device *handle;
-	int n;
-
-	io[0] = 0;
-	io[1] = 0;
-	io[2] = 1 << (3 - 1);
-	io[3] = PTTState << (3 - 1);
-	io[4] = 0;
-
-	if (CM108Device == NULL)
-		return;
-
-#ifdef WIN32
-	handle = hid_open_path(CM108Device);
-
-	if (!handle) {
-		printf("unable to open device\n");
-		return;
-	}
-
-	n = hid_write(handle, io, 5);
-	if (n < 0)
-	{
-		printf("Unable to write()\n");
-		printf("Error: %ls\n", hid_error(handle));
-	}
-
-	hid_close(handle);
-
-#else
-
-	int fd;
-
-	fd = open(CM108Device, O_WRONLY);
-
-	if (fd == -1)
-	{
-		printf("Could not open %s for write, errno=%d\n", CM108Device, errno);
-		return;
-	}
-
-	io[0] = 0;
-	io[1] = 0;
-	io[2] = 1 << (3 - 1);
-	io[3] = PTTState << (3 - 1);
-	io[4] = 0;
-
-	n = write(fd, io, 5);
-	if (n != 5)
-	{
-		printf("Write to %s failed, n=%d, errno=%d\n", CM108Device, n, errno);
-	}
-
-	close(fd);
-#endif
-	return;
-
-}
-
-
-
-void RadioPTT(int snd_ch, BOOL PTTState)
-{
-#ifdef __ARM_ARCH
-	if (useGPIO)
-	{
-		if (DualPTT && modemtoSoundLR[snd_ch] == 1)
-			gpioWrite(pttGPIOPinR, (pttGPIOInvert ? (1 - PTTState) : (PTTState)));
-		else
-			gpioWrite(pttGPIOPin, (pttGPIOInvert ? (1 - PTTState) : (PTTState)));
-
-		return;
-	}
-
-#endif
-
-	if ((PTTMode & PTTCM108))
-	{
-		CM108_set_ptt(PTTState);
-		return;
-	}
-	
-	if ((PTTMode & PTTHAMLIB))
-	{
-		HAMLIBSetPTT(PTTState);
-		return;
-	}
-	if (hPTTDevice == 0)
-		return;
-
-	if ((PTTMode & PTTCAT))
-	{
-		if (PTTState)
-			WriteCOMBlock(hPTTDevice, PTTOnCmd, PTTOnCmdLen);
-		else
-			WriteCOMBlock(hPTTDevice, PTTOffCmd, PTTOffCmdLen);
-
-		return;
-	}
-
-	if (DualPTT && modemtoSoundLR[snd_ch] == 1)		// use DTR
-	{
-		if (PTTState)
-			COMSetDTR(hPTTDevice);
-		else
-			COMClearDTR(hPTTDevice);
-	}
-	else
-	{
-		if ((PTTMode & PTTRTS))
-		{
-			if (PTTState)
-				COMSetRTS(hPTTDevice);
-			else
-				COMClearRTS(hPTTDevice);
-		}
-	}
-
-}
-
-char ShortDT[] = "HH:MM:SS";
-
-char * ShortDateTime()
-{
-	struct tm * tm;
-	time_t NOW = time(NULL);
-
-	tm = gmtime(&NOW);
-
-	sprintf(ShortDT, "%02d:%02d:%02d", tm->tm_hour, tm->tm_min, tm->tm_sec);
-	return ShortDT;
-}
-
-
-// Reed Solomon Stuff
-
-
-int NPAR = -1;	// Number of Parity Bytes - used in RS Code
-
-int xMaxErrors = 0;
-
-int RSEncode(UCHAR * bytToRS, UCHAR * RSBytes, int DataLen, int RSLen)
-{
-	// This just returns the Parity Bytes. I don't see the point
-	// in copying the message about
-
-	unsigned char Padded[256];		// The padded Data
-
-	int Length = DataLen + RSLen;	// Final Length of packet
-	int PadLength = 255 - Length;	// Padding bytes needed for shortened RS codes
-
-	//	subroutine to do the RS encode. For full length and shortend RS codes up to 8 bit symbols (mm = 8)
-
-	if (NPAR != RSLen)		// Changed RS Len, so recalc constants;
-	{
-		NPAR = RSLen;
-		xMaxErrors = NPAR / 2;
-		initialize_ecc();
-	}
-
-	// Copy the supplied data to end of data array.
-
-	memset(Padded, 0, PadLength);
-	memcpy(&Padded[PadLength], bytToRS, DataLen);
-
-	encode_data(Padded, 255 - RSLen, RSBytes);
-
-	return RSLen;
-}
-
-//	Main RS decode function
-
-extern int index_of[];
-extern int recd[];
-extern int Corrected[256];
-extern int tt;		//  number of errors that can be corrected 
-extern int kk;		// Info Symbols
-
-extern BOOL blnErrorsCorrected;
-
-
-BOOL RSDecode(UCHAR * bytRcv, int Length, int CheckLen, BOOL * blnRSOK)
-{
-
-
-	// Using a modified version of Henry Minsky's code
-
-	//Copyright Henry Minsky (hqm@alum.mit.edu) 1991-2009
-
-	// Rick's Implementation processes the byte array in reverse. and also 
-	//	has the check bytes in the opposite order. I've modified the encoder
-	//	to allow for this, but so far haven't found a way to mske the decoder
-	//	work, so I have to reverse the data and checksum to decode G8BPQ Nov 2015
-
-	//	returns TRUE if was ok or correction succeeded, FALSE if correction impossible
-
-	UCHAR intTemp[256];				// WOrk Area to pass to Decoder		
-	int i;
-	UCHAR * ptr2 = intTemp;
-	UCHAR * ptr1 = &bytRcv[Length - CheckLen - 1]; // Last Byte of Data
-
-	int DataLen = Length - CheckLen;
-	int PadLength = 255 - Length;		// Padding bytes needed for shortened RS codes
-
-	*blnRSOK = FALSE;
-
-	if (Length > 255 || Length < (1 + CheckLen))		//Too long or too short 
-		return FALSE;
-
-	if (NPAR != CheckLen)		// Changed RS Len, so recalc constants;
-	{
-		NPAR = CheckLen;
-		xMaxErrors = NPAR / 2;
-
-		initialize_ecc();
-	}
-
-
-	//	We reverse the data while zero padding it to speed things up
-
-	//	We Need (Data Reversed) (Zero Padding) (Checkbytes Reversed)
-
-	// Reverse Data
-
-	for (i = 0; i < DataLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	//	Clear padding
-
-	memset(ptr2, 0, PadLength);
-
-	ptr2 += PadLength;
-
-	// Error Bits
-
-	ptr1 = &bytRcv[Length - 1];			// End of check bytes
-
-	for (i = 0; i < CheckLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	decode_data(intTemp, 255);
-
-	// check if syndrome is all zeros 
-
-	if (check_syndrome() == 0)
-	{
-		// RS ok, so no need to correct
-
-		*blnRSOK = TRUE;
-		return TRUE;		// No Need to Correct
-	}
-
-	if (correct_errors_erasures(intTemp, 255, 0, 0) == 0) // Dont support erasures at the momnet
-
-		// Uncorrectable
-
-		return FALSE;
-
-	// Data has been corrected, so need to reverse again
-
-	ptr1 = &intTemp[DataLen - 1];
-	ptr2 = bytRcv; // Last Byte of Data
-
-	for (i = 0; i < DataLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	// ?? Do we need to return the check bytes ??
-
-	// Yes, so we can redo RS Check on supposedly connected frame
-
-	ptr1 = &intTemp[254];	// End of Check Bytes
-
-	for (i = 0; i < CheckLen; i++)
-	{
-		*(ptr2++) = *(ptr1--);
-	}
-
-	return TRUE;
-}
-
-extern TStringList detect_list[5];
-extern TStringList detect_list_c[5];
-
-void ProcessPktFrame(int snd_ch, UCHAR * Data, int frameLen)
-{
-	string * pkt = newString();
-
-	stringAdd(pkt, Data, frameLen + 2);			// 2 for crc (not actually there)
-
-	analiz_frame(snd_ch, pkt, "ARDOP", 1);
-
-}
diff --git a/SMMain.c b/SMMain.c
index 1295175..24f6159 100644
--- a/SMMain.c
+++ b/SMMain.c
@@ -32,6 +32,8 @@ along with QtSoundModem.  If not, see http://www.gnu.org/licenses
 BOOL KISSServ;
 int KISSPort;
 
+int NeedWaterfallHeaders = 0;
+
 BOOL AGWServ;
 int AGWPort;
 
@@ -566,7 +568,7 @@ int Freq_Change(int Chan, int Freq)
 	tx_freq[Chan] = Freq;
 
 	pnt_change[Chan] = TRUE;
-	wf_pointer(Chan);
+	NeedWaterfallHeaders = TRUE;
 
 	return Freq;
 }
diff --git a/UZ7HOStuff-DESKTOP-MHE5LO8.h b/UZ7HOStuff-DESKTOP-MHE5LO8.h
deleted file mode 100644
index 20721cc..0000000
--- a/UZ7HOStuff-DESKTOP-MHE5LO8.h
+++ /dev/null
@@ -1,1110 +0,0 @@
-#pragma once
-
-//
-//	 My port of UZ7HO's Soundmodem
-//
-
-#define VersionString "0.0.0.67alpha-6"
-#define VersionBytes {0, 0, 0, 67}
-
-// Added FX25. 4x100 FEC and V27 not Working and disabled
-
-// 0.8 V27 now OK.
-
-// 0.9 Digipeating added
-
-// 0.10 Fix second channel tones and calibrate
-
-// 0.11 Fix allocation of sessions to correct modem
-//		Fix DCD
-//		Fix Monitoring of Multiline packets
-//		Fix possible saving of wrong center freq
-//		Limit TX sample Q in Linux
-//
-
-// 0.12	Add AGWPE monitoring of received frames
-//		Fix DCD Threshold
-//		Fix KISS transparency issue
-
-// 0.13 Fix sending last few bits in FX.25 Mode
-
-// 0.14 Add "Copy on Select" to Trace Window
-
-// 0.15 Limit Trace window to 10000 lines
-
-// 0.16 Fix overwriting monitor window after scrollback
-
-// 0.17	Add GPIO and CAT PTT
-
-// 0.18	Add CM108/119 PTT
-
-// 0.19 Fix scheduling KISS frames
-
-// 0.20 Debug code added to RR processing
-
-// 0.21	Fix AGW monitor of multiple line packets
-//		Close ax.25 sessions if AGW Host session closes
-
-// 0.22	Add FEC Count to Session Stats
-
-// 0.23 Retry DISC until UA received or retry count exceeded
-
-// 0.24	More fixes to DISC handling
-
-// 0.26 Add OSS PulseAudio and HAMLIB support
-
-// 0.27 Dynamically load PulseAudio modules
-
-// 0.28 Add ARDOPPacket Mode
-
-// 0.29 Fix saving settings and geometry on close
-// 0.30 Retructure code to build with Qt 5.3
-//      Fix crash in nogui mode if pulse requested but not available
-//		Try to fix memory leaks
-
-// 0.31 Add option to run modems in seprate threads
-
-// 0.32	Fix timing problem with AGW connect at startup
-//		Add Memory ARQ
-//		Add Single bit "Correction"
-//		Fix error in 31 when using multiple decoders
-
-// 0.33 Fix Single bit correction
-//		More memory leak fixes
-
-// 0.34 Add API to set Modem and Center Frequency
-//		Fix crash in delete_incoming_mycalls
-
-// 0.35 Return Version in AGW Extended g response
-
-// 0.36 Fix timing problem on startup
-
-// 0.37 Add scrollbars to Device and Modem dialogs
-
-// 0.38 Change default CM108 name to /dev/hidraw0 on Linux
-
-// 0.39	Dont try to display Message Boxes in nogui mode.
-//		Close Device and Modem dialogs on Accept or Reject
-//		Fix using HAMLIB in nogui mode
-
-// 0.40	Fix bug in frame optimize when using 6 char calls
-
-// 0.41	Fix "glitch" on waterfall markers when changing modem freqs 
-
-// 0.42	Add "Minimize to Tray" option
-
-// 0.43 Add Andy's on_SABM fix.
-//		Fix Crash if KISS Data sent to AGW port
-
-// 0.44 Add UDP bridge.
-
-// 0.45 Add two more modems.
-// 0.46 Fix two more modems.
-
-// 0.47 Fix suprious DM when host connection lost
-//		Add CWID
-
-// 0.48 Send FRMR for unrecognised frame types
-
-// 0.49 Add Andy's FEC Tag correlation coode
-
-// 0.50 Fix Waterfall display when only using right channel
-//		Allow 1200 baud fsk at other center freqs
-//		Add Port numbers to Window title and Try Icon tooltip
-//		Fix calculation of filters for multiple decoders
-//		Add RX Offset setting (for satellite operation
-
-// 0.51	Fix Multithreading with more that 2 modems
-
-// 0.52	Add Stdin as source on Linux
-
-// 0.53	Use Byte instead of byte as byte is defined in newer versions of gcc
-
-// 0.54 Fix for ALSA problem on new pi OS
-
-// 0.55 Fix for compiler error with newer compiler
-
-// 0.56	Fix errors in Config.cpp			June 22
-
-// 0.57	Add Restart Waterfall action		August 22
-
-// 0.58 Add RSID							Sept 2022
-
-// 0.59 Add config of Digi Calls			Dec 2022
-
-// 0.60 Allow ARDOP Packet on modems 2 to 4 March 2023
-
-// 0.61 Add il2p support					April 2023
-
-// 0.62										April 2023
-//	Add option to specify sound devices that aren't in list
-//	Add Save button to Modem dialog to save current tab without closing dialog
-//	Don't add plug: to Linux device addresses unless addr contains : (allows use of eg ARDOP)
-
-// 0.64 Fix sending ax.25 (broken in .61)
-
-// 0.65	Allow Set Modem command to use modem index as well as modem name
-
-// 0.66 Allow configuration of waterfall span	June 23
-//		Add Exclude
-
-// .67 Add extra modes RUH 4800 RUH 9600 QPSK 600 QPSK 2400	July 23
-//	   8PSK 900 added but not working
-//	   Fix loading txtail
-//	   Fix digipeating
-//	   Add MaxFrame to Modem Dialog
-
-#include <string.h>
-#include <stdlib.h>
-#include <math.h>
-#include <stdio.h>
-#include <ctype.h>
-#include <time.h>
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-#define UNUSED(x) (void)(x)
-
-#ifdef M_PI
-#undef M_PI
-#endif
-
-#define M_PI       3.1415926f
-
-#define pi M_PI
-
-#ifndef WIN32
-#define _strdup strdup
-#endif
-
-	//#define NULL ((void *)0)
-
-	//Delphi Types remember case insensitive
-
-#define single float
-#define boolean int
-#define Byte unsigned char		//                  0 to 255
-#define Word unsigned short	//                        0 to 65,535
-#define SmallInt short 		//                  -32,768 to 32,767
-#define LongWord unsigned int	//                        0 to 4,294,967,295
- //  Int6 : Cardinal; //                        0 to 4,294,967,295
-#define LongInt int			//           -2,147,483,648 to 2,147,483,647
-#define Integer int  //           -2,147,483,648 to 2,147,483,647
-//#define Int64 long long		 // -9,223,372,036,854,775,808 to 9,223,372,036,854,775,807
-
-//#define Byte unsigned char		//                  0 to 255
-#define word unsigned short	//                        0 to 65,535
-#define smallint short 		//                  -32,768 to 32,767
-#define longword unsigned int	//                        0 to 4,294,967,295
- //  Int6 : Cardinal; //                        0 to 4,294,967,295
-#define longint int			//           -2,147,483,648 to 2,147,483,647
-#define integer int  //           -2,147,483,648 to 2,147,483,647
-
-typedef unsigned long ULONG;
-
-#define UCHAR unsigned char
-#define UINT unsigned int
-#define BOOL int
-#define TRUE 1
-#define FALSE 0
-
-// Soundcard Channels
-
-#define NONE 0
-#define LEFT 1
-#define RIGHT 2
-
-#define nr_emph 2
-
-#define decodedNormal 4 //'-'
-#define decodedFEC    3 //'F'
-#define decodedMEM	  2 //'#'
-#define decodedSingle 1 //'$'
-
-
-// Think about implications of changing this !!
-extern int FFTSize;
-
-// Seems to use Delphi TStringList for a lot of queues. This seems to be a list of pointers and a count
-// Each pointer is to a Data/Length pair
-//Maybe something like
-
-typedef struct string_T
-{
-	unsigned char * Data;
-	int Length;
-	int AllocatedLength;				// A reasonable sized block is allocated at the start to speed up adding chars
-
-}string;
-
-typedef struct TStringList_T
-{
-	int Count;
-	string ** Items;
-
-} TStringList;
-
-// QPSK struct
-
-typedef struct TQPSK_t
-{
-	UCHAR tx[4];
-	int count[4];
-	UCHAR rx[4];
-	UCHAR mode;
-} TPQSK;
-
-
-typedef struct TKISSMode_t
-{
-	string * data_in;
-	void * Socket;				// Used as a key
-
-	// Not sure what rest are used for. Seems to be one per channel
-
-	TStringList buffer[4];			// Outgoing Frames
-
-} TKISSMode;
-
-typedef struct  TMChannel_t
-{
-
-	single prev_LPF1I_buf[4096];
-	single prev_LPF1Q_buf[4096];
-	single prev_dLPFI_buf[4096];
-	single prev_dLPFQ_buf[4096];
-	single prev_AFCI_buf[4096];
-	single prev_AFCQ_buf[4096];
-	single AngleCorr;
-	single MUX_osc;
-	single AFC_IZ1;
-	single AFC_IZ2;
-	single AFC_QZ1;
-	single AFC_QZ2;
-	single AFC_bit_buf1I[1024];
-	single AFC_bit_buf1Q[1024];
-	single AFC_bit_buf2[1024];
-	single AFC_IIZ1;
-	single AFC_QQZ1;
-
-} TMChannel;
-
-typedef struct TFX25_t
-{
-	string  data;
-	Byte  status;
-	Byte  bit_cnt;
-	Byte  byte_rx;
-	unsigned long long tag;
-	Byte  size;
-	Byte  rs_size;
-	Byte size_cnt;
-} TFX25;
-
-
-
-typedef struct TDetector_t
-{
-	struct TFX25_t fx25[4];
-	TStringList	mem_ARQ_F_buf[5];
-	TStringList mem_ARQ_buf[5];
-	float pll_loop[5];
-	float last_sample[5];
-	UCHAR ones[5];
-	UCHAR zeros[5];
-	float bit_buf[5][1024];
-	float bit_buf1[5][1024];
-	UCHAR sample_cnt[5];
-	UCHAR last_bit[5];
-	float PSK_IZ1[5];
-	float PSK_QZ1[5];
-	float PkAmpI[5];
-	float PkAmpQ[5];
-	float PkAmp[5];
-	float PkAmpMax[5];
-	int newpkpos[5];
-	float AverageAmp[5];
-	float AngleCorr[5];
-	float MinAmp[5];
-	float MaxAmp[5];
-	float MUX3_osc[5];
-	float MUX3_1_osc[5];
-	float MUX3_2_osc[5];
-	float Preemphasis6[5];
-	float Preemphasis12[5];
-	float PSK_AGC[5];
-	float AGC[5];
-	float AGC1[5];
-	float AGC2[5];
-	float AGC3[5];
-	float AGC_max[5];
-	float AGC_min[5];
-	float AFC_IZ1[5];
-	float AFC_IZ2[5];
-	float AFC_QZ1[5];
-	float AFC_QZ2[5];
-
-	UCHAR last_rx_bit[5];
-	UCHAR bit_stream[5];
-	UCHAR byte_rx[5];
-	UCHAR bit_stuff_cnt[5];
-	UCHAR bit_cnt[5];
-	float bit_osc[5];
-	UCHAR frame_status[5];
-	string rx_data[5];
-	string FEC_rx_data[5];
-	//
-	UCHAR FEC_pol[5];
-	unsigned short FEC_err[5];
-	unsigned long long FEC_header1[5][2];
-	unsigned short FEC_blk_int[5];
-	unsigned short FEC_len_int[5];
-	unsigned short FEC_len[5];
-
-	unsigned short FEC_len_cnt[5];
-	
-	UCHAR rx_intv_tbl[5][4];
-	UCHAR rx_intv_sym[5];
-	UCHAR rx_viterbi[5];
-	UCHAR viterbi_cnt[5];
-	//	  SurvivorStates [1..4,0..511] of TSurvivor;
-		  //
-	TMChannel MChannel[5][4];
-
-	float AFC_dF_avg[5];
-	float AFC_dF[5];
-	float AFC_bit_osc[5];
-	float AFC_bit_buf[5][1024];
-	unsigned short AFC_cnt[5];
-
-	string raw_bits1[5];
-	string raw_bits[5];
-	UCHAR last_nrzi_bit[5];
-
-	float BPF_core[5][2048];
-	float LPF_core[5][2048];
-
-	float src_INTR_buf[5][8192];
-	float src_INTRI_buf[5][8192];
-	float src_INTRQ_buf[5][8192];
-	float src_LPF1I_buf[5][8192];
-	float src_LPF1Q_buf[5][8192];
-
-	float src_BPF_buf[5][2048];
-	float src_Loop_buf[5][8192];
-	float prev_BPF_buf[5][4096];
-
-	float prev_LPF1I_buf[5][4096];
-	float prev_LPF1Q_buf[5][4096];
-	float prev_INTR_buf[5][16384];
-	float prev_INTRI_buf[5][16384];
-	float prev_INTRQ_buf[5][16384];
-
-	Byte emph_decoded;	
-	Byte rx_decoded;
-	Byte errors;
-
-} TDetector;
-
-
-
-typedef struct AGWUser_t
-{
-	void *socket;
-	string * data_in;
-	TStringList AGW_frame_buf;
-	boolean	Monitor;
-	boolean	Monitor_raw;
-	boolean reportFreqAndModem;			// Can report modem and frequency to host
-
-} AGWUser;
-
-typedef struct  TAX25Info_t
-{
-	longint	stat_s_pkt;
-	longint stat_s_byte;
-	longint stat_r_pkt;
-	longint stat_r_byte;
-	longint stat_r_fc;
-	longint stat_fec_count;
-	time_t stat_begin_ses;
-	time_t stat_end_ses;
-	longint stat_l_r_byte;
-	longint stat_l_s_byte;
-
-} TAX25Info;
-
-typedef struct TAX25Port_t
-{
-	Byte hi_vs;
-	Byte vs;
-	Byte vr;
-	Byte PID;
-	TStringList in_data_buf;
-	TStringList frm_collector;
-	string frm_win[8];
-	string out_data_buf;
-	word t1;
-	word t2;
-	word t3;
-	Byte i_lo;
-	Byte i_hi;
-	word n1;
-	word n2;
-	word IPOLL_cnt;
-	TStringList frame_buf; //����� ������ �� ��������
-	TStringList I_frame_buf;
-	Byte status;
-	word clk_frack;
-	char corrcall[10];
-	char mycall[10];
-	UCHAR digi[56];
-	UCHAR Path[80];				// Path in ax25 format - added to save building it each time
-	UCHAR ReversePath[80];
-	int snd_ch;					// Simplifies parameter passing
-	int port;
-	int pathLen;
-	void * socket;
-	char kind[16];
-	TAX25Info info;
-} TAX25Port;
-
-
-#define LOGEMERGENCY 0 
-#define LOGALERT 1
-#define LOGCRIT 2 
-#define LOGERROR 3 
-#define LOGWARNING 4
-#define LOGNOTICE 5
-#define LOGINFO 6
-#define LOGDEBUG 7
-
-#define PTTRTS		1
-#define PTTDTR		2
-#define PTTCAT		4
-#define PTTCM108	8
-#define PTTHAMLIB	16
-
-// Status flags
-
-#define STAT_NO_LINK  0
-#define STAT_LINK 1
-#define STAT_CHK_LINK 2
-#define STAT_WAIT_ANS 3
-#define STAT_TRY_LINK 4
-#define STAT_TRY_UNLINK 5
-
-
-	// �md,Resp,Poll,Final,Digipeater flags
-#define 	SET_P 1
-#define 	SET_F 0
-#define 	SET_C 1
-#define 	SET_R 0
-#define 	SET_NO_RPT 0
-#define 	SET_RPT 1
-	// Frame ID flags
-#define 	I_FRM 0
-#define 	S_FRM 1
-#define 	U_FRM 2
-#define 	I_I 0
-#define 	S_RR 1
-#define 	S_RNR 5
-#define 	S_REJ 9
-#define		S_SREJ 0x0D
-#define 	U_SABM 47
-#define 	U_DISC 67
-#define 	U_DM 15
-#define 	U_UA 99
-#define 	U_FRMR 135
-#define 	U_UI 3
-	// PID flags
-#define 	PID_X25 0x01       // 00000001-CCIT X25 PLP
-#define 	PID_SEGMENT 0x08   // 00001000-Segmentation fragment
-#define 	PID_TEXNET 0xC3    // 11000011-TEXNET Datagram Protocol
-#define 	PID_LQ 0xC4        // 11001000-Link Quality Protocol
-#define 	PID_APPLETALK 0xCA // 11001010-Appletalk
-#define 	PID_APPLEARP 0xCB  // 11001011-Appletalk ARP
-#define 	PID_IP 0xCC        // 11001100-ARPA Internet Protocol
-#define 	PID_ARP 0xCD       // 11001101-ARPA Address Resolution Protocol
-#define 	PID_NET_ROM 0xCF   // 11001111-NET/ROM
-
-
-//	Sound interface buffer sizes
-
-extern int ReceiveSize;
-extern int SendSize;
-
-#define NumberofinBuffers 4
-
-#define Now getTicks()
-
-// #defines from all modules (?? is this a good idaa ??
-
-#define WIN_MAXIMIZED 0
-#define WIN_MINIMIZED 1
-#define MODEM_CAPTION 'SoundModem by UZ7HO'
-#define MODEM_VERSION '1.06'
-#define SND_IDLE 0
-#define SND_TX 1
-#define BUF_EMPTY 0
-#define BUF_FULL 1
-#define DISP_MONO FALSE
-#define DISP_RGB TRUE
-#define MOD_IDLE 0
-#define MOD_RX 1
-#define MOD_TX 2
-#define MOD_WAIT 3
-#define TIMER_FREE 0
-#define TIMER_BUSY 1
-#define TIMER_OFF 2
-#define TIMER_EVENT_ON 3
-#define TIMER_EVENT_OFF 4
-#define DEBUG_TIMER 1
-#define DEBUG_WATERFALL 2
-#define DEBUG_DECODE 4
-#define DEBUG_SOUND 8
-#define IS_LAST TRUE
-#define IS_NOT_LAST FALSE
-#define modes_count 20
-#define SPEED_300 0
-#define SPEED_1200 1
-#define SPEED_600 2
-#define SPEED_2400 3
-#define SPEED_P1200 4
-#define SPEED_P600 5
-#define SPEED_P300 6
-#define SPEED_P2400 7
-#define SPEED_Q4800 8
-#define SPEED_Q3600 9
-#define SPEED_Q2400 10
-#define SPEED_MP400 11
-#define SPEED_DW2400 12
-#define SPEED_8P4800 13
-#define SPEED_2400V26B 14
-#define SPEED_ARDOP 15
-#define SPEED_Q300 16
-#define SPEED_8PSK300 17
-#define SPEED_RUH48 18
-#define SPEED_RUH96 19
-
-#define MODE_FSK 0
-#define MODE_BPSK 1
-#define MODE_QPSK 2
-#define MODE_MPSK 3
-#define MODE_8PSK 4
-#define MODE_PI4QPSK 5
-#define MODE_ARDOP 6
-#define MODE_RUH 7
-
-#define QPSK_SM 0
-#define QPSK_V26 1
-
-#define MODEM_8P4800_BPF 3200
-#define MODEM_8P4800_TXBPF 3400
-#define MODEM_8P4800_LPF 1000
-#define MODEM_8P4800_BPF_TAP 64
-#define MODEM_8P4800_LPF_TAP 8
- //
-#define MODEM_MP400_BPF 775
-#define MODEM_MP400_TXBPF 850
-#define MODEM_MP400_LPF 70
-#define MODEM_MP400_BPF_TAP 256
-#define MODEM_MP400_LPF_TAP 128
- //
-#define MODEM_DW2400_BPF 2400
-#define MODEM_DW2400_TXBPF 2500
-#define MODEM_DW2400_LPF 900
-#define MODEM_DW2400_BPF_TAP 256 //256
-#define MODEM_DW2400_LPF_TAP 32  //128
- //
-#define MODEM_Q2400_BPF 2400
-#define MODEM_Q2400_TXBPF 2500
-#define MODEM_Q2400_LPF 900
-#define MODEM_Q2400_BPF_TAP 256 //256
-#define MODEM_Q2400_LPF_TAP 128  //128
- //
-#define MODEM_Q3600_BPF 3600
-#define MODEM_Q3600_TXBPF 3750
-#define MODEM_Q3600_LPF 1350
-#define MODEM_Q3600_BPF_TAP 256
-#define MODEM_Q3600_LPF_TAP 128
- //
-#define MODEM_Q4800_BPF 4800
-#define MODEM_Q4800_TXBPF 5000
-#define MODEM_Q4800_LPF 1800
-#define MODEM_Q4800_BPF_TAP 256
-#define MODEM_Q4800_LPF_TAP 128
- //
-#define MODEM_P2400_BPF 4800
-#define MODEM_P2400_TXBPF 5000
-#define MODEM_P2400_LPF 1800
-#define MODEM_P2400_BPF_TAP 256
-#define MODEM_P2400_LPF_TAP 128
- //
-#define MODEM_P1200_BPF 2400
-#define MODEM_P1200_TXBPF 2500
-#define MODEM_P1200_LPF 900
-#define MODEM_P1200_BPF_TAP 256
-#define MODEM_P1200_LPF_TAP 128
- //
-#define MODEM_P600_BPF 1200
-#define MODEM_P600_TXBPF 1250
-#define MODEM_P600_LPF 400
-#define MODEM_P600_BPF_TAP 256
-#define MODEM_P600_LPF_TAP 128
- //
-#define MODEM_P300_BPF 600
-#define MODEM_P300_TXBPF 625
-#define MODEM_P300_LPF 200
-#define MODEM_P300_BPF_TAP 256
-#define MODEM_P300_LPF_TAP 128
- //
-#define MODEM_300_BPF 500
-#define MODEM_300_TXBPF 500
-#define MODEM_300_LPF 155
-#define MODEM_300_BPF_TAP 256
-#define MODEM_300_LPF_TAP 128
- //
-#define MODEM_600_BPF 800
-#define MODEM_600_TXBPF 900
-#define MODEM_600_LPF 325
-#define MODEM_600_BPF_TAP 256
-#define MODEM_600_LPF_TAP 128
- //
-#define MODEM_1200_BPF 1400
-#define MODEM_1200_TXBPF 1600
-#define MODEM_1200_LPF 650
-#define MODEM_1200_BPF_TAP 256
-#define MODEM_1200_LPF_TAP 128
- //
-#define MODEM_2400_BPF 3200
-#define MODEM_2400_TXBPF 3200
-#define MODEM_2400_LPF 1400
-#define MODEM_2400_BPF_TAP 256
-#define MODEM_2400_LPF_TAP 128
-
-#define TX_SILENCE 0
-#define TX_DELAY 1
-#define TX_TAIL 2
-#define TX_NO_DATA 3
-#define TX_FRAME 4
-#define TX_WAIT_BPF 5
-
-
-#define FRAME_WAIT 0
-#define FRAME_LOAD 1
-#define RX_BIT0 0
-#define RX_BIT1 128
-#define DCD_WAIT_SLOT 0
-#define DCD_WAIT_PERSIST 1
-
-#define FX25_MODE_NONE  0
-#define FX25_MODE_RX  1
-#define FX25_MODE_TXRX 2
-#define FX25_TAG 0
-#define FX25_LOAD 1
-
-#define IL2P_MODE_NONE  0
-#define IL2P_MODE_RX  1				// RX il2p + HDLC
-#define IL2P_MODE_TXRX 2
-#define IL2P_MODE_ONLY 3			// RX only il2p, TX il2p
-
-
-#define    MODE_OUR 0
-#define    MODE_OTHER 1
-#define    MODE_RETRY 2
-
-#define FRAME_FLAG 126		// 7e
-
-#define port_num 32		// ?? Max AGW sessions
-#define PKT_ERR 17		// Minimum packet size, bytes
-#define I_MAX 7			// Maximum number of packets
-
-
-	// externs for all modules
-
-#define ARDOPBufferSize 12000 * 100
-
-extern short ARDOPTXBuffer[4][ARDOPBufferSize];	// Enough to hold whole frame of samples
-
-extern int ARDOPTXLen[4];				// Length of frame
-extern int ARDOPTXPtr[4];				// Tx Pointer
-
-extern BOOL KISSServ;
-extern int KISSPort;
-
-extern BOOL AGWServ;
-extern int AGWPort;
-
-extern TStringList KISS_acked[];
-extern TStringList KISS_iacked[];
-
-extern TStringList all_frame_buf[5];
-
-extern unsigned short pkt_raw_min_len;
-extern int stat_r_mem;
-
-extern UCHAR diddles;
-
-extern int stdtones;
-extern int fullduplex;
-
-extern struct TQPSK_t qpsk_set[4];
-
-extern int NonAX25[5];
-
-extern short txtail[5];
-extern short txdelay[5];
-
-extern short modem_def[5];
-
-extern int emph_db[5];
-extern UCHAR emph_all[5];
-
-extern UCHAR modem_mode[5];
-
-extern UCHAR RCVR[5];
-extern int soundChannel[5];
-extern int modemtoSoundLR[4];
-
-extern short rx_freq[5];
-extern short active_rx_freq[5];
-extern short rx_shift[5];
-extern short rx_baudrate[5];
-extern short rcvr_offset[5];
-
-extern int tx_hitoneraisedb[5];
-extern float tx_hitoneraise[5];
-
-
-extern UCHAR tx_status[5];
-extern float tx_freq[5];
-extern float tx_shift[5];
-extern unsigned short tx_baudrate[5];
-extern unsigned short tx_bitrate[5];
-
-extern unsigned short bpf[5];
-extern unsigned short lpf[5];
-
-extern unsigned short txbpf[5];
-
-extern unsigned short  tx_BPF_tap[5];
-extern unsigned short  tx_BPF_timer[5];
-
-extern unsigned short  BPF_tap[5];
-extern unsigned short  LPF_tap[5];
-
-extern float tx_BPF_core[5][32768];
-extern float LPF_core[5][2048];
-
-extern UCHAR xData[256];
-extern UCHAR xEncoded[256];
-extern UCHAR xDecoded[256];
-
-extern float PI125;
-extern float PI375;
-extern float PI625;
-extern float PI875;
-extern 	float PI5;
-extern float PI25;
-extern float PI75;
-
-extern int max_frame_collector[4];
-extern boolean KISS_opt[4];
-
-#define MaxErrors 4
-
-extern BOOL MinOnStart;
-
-//RS TReedSolomon;
-//  Form1 TForm1;
-//  WaveFormat TWaveFormatEx;
-
-extern int UDPServ;
-extern long long udpServerSeqno;
-
-extern int Channels;
-extern int BitsPerSample;
-extern float TX_Samplerate;
-extern float RX_Samplerate;
-extern int RX_SR;
-extern int TX_SR;
-extern int RX_PPM;
-extern int TX_PPM;
-extern int tx_bufsize;
-extern int rx_bufsize;
-extern int tx_bufcount;
-extern int rx_bufcount;
-extern int fft_size;
-extern int  mouse_down[2];
-//UCHAR * RX_pBuf array[257];
-//  RX_header array[1..256] of TWaveHdr;
-//  TX_pBuf array[1..4,1..256] of pointer;
-//TX_header array[1..4,1..256] of TWaveHdr;
-extern UCHAR calib_mode[5];
-extern UCHAR snd_status[5];
-extern UCHAR buf_status[5];
-extern UCHAR tx_buf_num1[5];
-extern UCHAR tx_buf_num[5];
-extern int speed[5];
-extern int panels[6];
-
-extern int FFTSize;
-#define fft_size FFTSize
-
-extern float fft_window_arr[2048];
-//  fft_s,fft_d array[0..2047] of TComplex;
-extern short fft_buf[2][8192];
-extern UCHAR fft_disp[2][1024];
-//  bm array[1..4] of TBitMap;
-//  bm1,bm2,bm3 TBitMap;
-
-//  WaveInHandle hWaveIn;
-//  WaveOutHandle array[1..4] of hWaveOut;
-extern int RXBufferLength;
-
-// data1 PData16;
-
-extern int grid_time;
-extern int fft_mult;
-extern int fft_spd;
-extern int grid_timer;
-extern int stop_wf;
-extern int raduga;
-extern char snd_rx_device_name[32];
-extern char snd_tx_device_name[32];
-extern int snd_rx_device;
-extern int snd_tx_device;
-extern UCHAR mod_icon_status;
-extern UCHAR last_mod_icon_status;
-extern UCHAR icon_timer;
-//  TelIni TIniFile;
-extern char cur_dir[];
-//  TimerId1 cardinal;
-//  TimerId2 cardinal;
-extern UCHAR TimerStat1;
-extern UCHAR TimerStat2;
-extern int stat_log;
-
-extern char PTTPort[80];			// Port for Hardware PTT - may be same as control port.
-extern int PTTMode;
-extern int PTTBAUD ;
-
-extern char PTTOnString[128];
-extern char PTTOffString[128];
-
-extern UCHAR PTTOnCmd[64];
-extern UCHAR PTTOnCmdLen;
-
-extern UCHAR PTTOffCmd[64];
-extern UCHAR PTTOffCmdLen;
-
-extern int PTT_device;
-extern int RX_device;
-extern int TX_device;
-extern int TX_rotate;
-extern int UsingLeft;
-extern int UsingRight;
-extern int UsingBothChannels;
-extern int pttGPIOPin;
-extern int pttGPIOPinR;
-extern BOOL pttGPIOInvert;
-extern BOOL useGPIO;
-extern BOOL gotGPIO;
-extern int VID;
-extern int PID;
-extern char CM108Addr[80];
-extern int HamLibPort;
-extern char HamLibHost[];
-
-extern int SCO;
-extern int DualPTT;
-extern UCHAR  DebugMode;
-extern UCHAR TimerEvent;
-extern int nr_monitor_lines;
-extern int UTC_Tim;
-extern int MainPriority;
-//  MainThreadHandle THandle;
-extern UCHAR w_state;
-
-extern BOOL Firstwaterfall;
-extern BOOL Secondwaterfall;
-
-extern int dcd_threshold;
-extern int rxOffset;
-extern int chanOffset[4];
-extern int Continuation[4];	// Sending 2nd or more packet of burst
-
-extern boolean busy;
-extern boolean dcd[5];
-
-extern struct TKISSMode_t  KISS;
-
-extern boolean dyn_frack[4] ;
-extern Byte recovery[4];
-extern Byte users[4];
-
-extern int resptime[4];
-extern int slottime[4];
-extern int persist[4];
-extern int fracks[4];
-extern int frack_time[4];
-extern int idletime[4];
-extern int redtime[4];
-extern int IPOLL[4];
-extern int maxframe[4];
-extern int TXFrmMode[4];
-
-extern char MyDigiCall[4][512];
-extern char exclude_callsigns[4][512];
-extern char exclude_APRS_frm[4][512];
-
-extern TStringList  list_exclude_callsigns[4];
-extern TStringList list_exclude_APRS_frm[4];
-extern TStringList list_digi_callsigns[4];
-
-
-extern int SoundIsPlaying;
-extern int Capturing;
-
-extern struct TDetector_t  DET[nr_emph + 1][16];
-
-extern char CaptureDevice[80];
-extern char PlaybackDevice[80];
-
-extern TAX25Port AX25Port[4][port_num];
-
-extern int fx25_mode[4];
-extern int il2p_mode[4];
-
-extern int tx_fx25_size[4];
-extern int tx_fx25_size_cnt[4];
-extern int tx_fx25_mode[4];
-
-extern int SatelliteMode;
-
-extern int using48000;			// Set if using 48K sample rate (ie RUH Modem active)
-
-
-// Function prototypes
-
-void KISS_send_ack(UCHAR port, string * data);
-void AGW_AX25_frame_analiz(int snd_ch, int RX, string * frame);
-void FIR_filter(float * src, unsigned short buf_size, unsigned short tap, float * core, float * dest, float * prev);
-void make_core_TXBPF(UCHAR snd_ch, float freq, float width);
-void OpenPTTPort();
-void ClosePTTPort();
-
-void RadioPTT(int snd_ch, BOOL PTTState);
-void put_frame(int snd_ch, string * frame, char * code, int  tx_stat, int excluded);
-void CloseCOMPort(int fd);
-void COMClearRTS(int fd);
-void COMClearDTR(int fd);
-unsigned int getTicks();
-char * ShortDateTime();
-void  write_ax25_info(TAX25Port * AX25Sess);
-void reverse_addr(Byte * path, Byte * revpath, int Len);
-string * get_mycall(string * path);
-TAX25Port * get_user_port_by_calls(int snd_ch, char *  CallFrom, char *  CallTo);
-TAX25Port * get_free_port(int snd_ch);
-void * in_list_incoming_mycall(Byte * path);
-boolean add_incoming_mycalls(void * socket, char * src_call);
-int get_addr(char * Calls, UCHAR * AXCalls);
-void reverse_addr(Byte * path, Byte * revpath, int Len);
-void set_link(TAX25Port * AX25Sess, UCHAR * axpath);
-void rst_timer(TAX25Port * AX25Sess);
-void set_unlink(TAX25Port * AX25Sess, Byte * path);
-unsigned short get_fcs(UCHAR * Data, unsigned short len);
-void KISSSendtoServer(void * sock, Byte * Msg, int Len);
-int ConvFromAX25(unsigned char * incall, char * outcall);
-BOOL ConvToAX25(char * callsign, unsigned char * ax25call);
-void Debugprintf(const char * format, ...);
-
-double pila(double x);
-
-void AGW_Raw_monitor(int snd_ch, string * data);
-
-// Delphi emulation functions
-
-string * Strings(TStringList * Q, int Index);
-void Clear(TStringList * Q);
-int Count(TStringList * List);
-
-string * newString();
-string * copy(string * Source, int StartChar, int Count);
-TStringList * newTStringList();
-
-void freeString(string * Msg);
-
-void initString(string * S);
-void initTStringList(TStringList* T);
-
-// Two delete() This is confusing!!
-// Not really - one acts on String, other TStringList
-
-void Delete(TStringList * Q, int Index);
-void mydelete(string * Source, int StartChar, int Count);
-
-void move(UCHAR * SourcePointer, UCHAR * DestinationPointer, int CopyCount);
-void fmove(float * SourcePointer, float * DestinationPointer, int CopyCount);
-
-void setlength(string * Msg, int Count);		// Set string length
-
-string * stringAdd(string * Msg, UCHAR * Chars, int Count);		// Extend string 
-
-void Assign(TStringList * to, TStringList * from);	// Duplicate from to to
-
-string * duplicateString(string * in);
-
-// This looks for a string in a stringlist. Returns inhex if found, otherwise -1
-
-int  my_indexof(TStringList * l, string * s);
-
-boolean compareStrings(string * a, string * b);
-
-int Add(TStringList * Q, string * Entry);
-
-
-#define IL2P_SYNC_WORD_SIZE 3
-#define IL2P_HEADER_SIZE 13	// Does not include 2 parity.
-#define IL2P_HEADER_PARITY 2
-
-#define IL2P_MAX_PAYLOAD_SIZE 1023
-#define IL2P_MAX_PAYLOAD_BLOCKS 5
-#define IL2P_MAX_PARITY_SYMBOLS 16		// For payload only.
-#define IL2P_MAX_ENCODED_PAYLOAD_SIZE (IL2P_MAX_PAYLOAD_SIZE + IL2P_MAX_PAYLOAD_BLOCKS * IL2P_MAX_PARITY_SYMBOLS)
-
-struct il2p_context_s {
-
-	enum { IL2P_SEARCHING = 0, IL2P_HEADER, IL2P_PAYLOAD, IL2P_DECODE } state;
-
-	unsigned int acc;	// Accumulate most recent 24 bits for sync word matching.
-				// Lower 8 bits are also used for accumulating bytes for
-				// the header and payload.
-
-	int bc;			// Bit counter so we know when a complete byte has been accumulated.
-
-	int polarity;		// 1 if opposite of expected polarity.
-
-	unsigned char shdr[IL2P_HEADER_SIZE + IL2P_HEADER_PARITY];
-	// Scrambled header as received over the radio.  Includes parity.
-	int hc;			// Number if bytes placed in above.
-
-	unsigned char uhdr[IL2P_HEADER_SIZE];  // Header after FEC and unscrambling.
-
-	int eplen;		// Encoded payload length.  This is not the nuumber from
-				// from the header but rather the number of encoded bytes to gather.
-
-	unsigned char spayload[IL2P_MAX_ENCODED_PAYLOAD_SIZE];
-	// Scrambled and encoded payload as received over the radio.
-	int pc;			// Number of bytes placed in above.
-
-	int corrected;		// Number of symbols corrected by RS FEC.
-};
-
-
-#ifdef __cplusplus
-}
-#endif
\ No newline at end of file
diff --git a/UZ7HOStuff-HPLaptop.h b/UZ7HOStuff-HPLaptop.h
deleted file mode 100644
index dfc2886..0000000
--- a/UZ7HOStuff-HPLaptop.h
+++ /dev/null
@@ -1,1023 +0,0 @@
-//
-//	 My port of UZ7HO's Soundmodem
-//
-
-#define VersionString "0.0.0.59"
-#define VersionBytes {0, 0, 0, 59}
-
-// Added FX25. 4x100 FEC and V27 not Working and disabled
-
-// 0.8 V27 now OK.
-
-// 0.9 Digipeating added
-
-// 0.10 Fix second channel tones and calibrate
-
-// 0.11 Fix allocation of sessions to correct modem
-//		Fix DCD
-//		Fix Monitoring of Multiline packets
-//		Fix possible saving of wrong center freq
-//		Limit TX sample Q in Linux
-//
-
-// 0.12	Add AGWPE monitoring of received frames
-//		Fix DCD Threshold
-//		Fix KISS transparency issue
-
-// 0.13 Fix sending last few bits in FX.25 Mode
-
-// 0.14 Add "Copy on Select" to Trace Window
-
-// 0.15 Limit Trace window to 10000 lines
-
-// 0.16 Fix overwriting monitor window after scrollback
-
-// 0.17	Add GPIO and CAT PTT
-
-// 0.18	Add CM108/119 PTT
-
-// 0.19 Fix scheduling KISS frames
-
-// 0.20 Debug code added to RR processing
-
-// 0.21	Fix AGW monitor of multiple line packets
-//		Close ax.25 sessions if AGW Host session closes
-
-// 0.22	Add FEC Count to Session Stats
-
-// 0.23 Retry DISC until UA received or retry count exceeded
-
-// 0.24	More fixes to DISC handling
-
-// 0.26 Add OSS PulseAudio and HAMLIB support
-
-// 0.27 Dynamically load PulseAudio modules
-
-// 0.28 Add ARDOPPacket Mode
-
-// 0.29 Fix saving settings and geometry on close
-// 0.30 Retructure code to build with Qt 5.3
-//      Fix crash in nogui mode if pulse requested but not available
-//		Try to fix memory leaks
-
-// 0.31 Add option to run modems in seprate threads
-
-// 0.32	Fix timing problem with AGW connect at startup
-//		Add Memory ARQ
-//		Add Single bit "Correction"
-//		Fix error in 31 when using multiple decoders
-
-// 0.33 Fix Single bit correction
-//		More memory leak fixes
-
-// 0.34 Add API to set Modem and Center Frequency
-//		Fix crash in delete_incoming_mycalls
-
-// 0.35 Return Version in AGW Extended g response
-
-// 0.36 Fix timing problem on startup
-
-// 0.37 Add scrollbars to Device and Modem dialogs
-
-// 0.38 Change default CM108 name to /dev/hidraw0 on Linux
-
-// 0.39	Dont try to display Message Boxes in nogui mode.
-//		Close Device and Modem dialogs on Accept or Reject
-//		Fix using HAMLIB in nogui mode
-
-// 0.40	Fix bug in frame optimize when using 6 char calls
-
-// 0.41	Fix "glitch" on waterfall markers when changing modem freqs 
-
-// 0.42	Add "Minimize to Tray" option
-
-// 0.43 Add Andy's on_SABM fix.
-//		Fix Crash if KISS Data sent to AGW port
-
-// 0.44 Add UDP bridge.
-
-// 0.45 Add two more modems.
-// 0.46 Fix two more modems.
-
-// 0.47 Fix suprious DM when host connection lost
-//		Add CWID
-
-// 0.48 Send FRMR for unrecognised frame types
-
-// 0.49 Add Andy's FEC Tag correlation coode
-
-// 0.50 Fix Waterfall display when only using right channel
-//		Allow 1200 baud fsk at other center freqs
-//		Add Port numbers to Window title and Try Icon tooltip
-//		Fix calculation of filters for multiple decoders
-//		Add RX Offset setting (for satellite operation
-
-// 0.51	Fix Multithreading with more that 2 modems
-
-// 0.52	Add Stdin as source on Linux
-
-// 0.53	Use Byte instead of byte as byte is defined in newer versions of gcc
-
-// 0.54 Fix for ALSA problem on new pi OS
-
-// 0.55 Fix for compiler error with newer compiler
-
-// 0.56	Fix errors in Config.cpp			June 22
-
-// 0.57	Add Restart Waterfall action		August 22
-
-// 0.58 Add RSID							Sept 2022
-
-// 0.59 Add config of Digi Calls			Dec 2022
-
-#include <string.h>
-#include <stdlib.h>
-#include <math.h>
-#include <stdio.h>
-#include <ctype.h>
-#include <time.h>
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-#define UNUSED(x) (void)(x)
-
-#ifdef M_PI
-#undef M_PI
-#endif
-
-#define M_PI       3.1415926f
-
-#define pi M_PI
-
-#ifndef WIN32
-#define _strdup strdup
-#endif
-
-	//#define NULL ((void *)0)
-
-	//Delphi Types remember case insensitive
-
-#define single float
-#define boolean int
-#define Byte unsigned char		//                  0 to 255
-#define Word unsigned short	//                        0 to 65,535
-#define SmallInt short 		//                  -32,768 to 32,767
-#define LongWord unsigned int	//                        0 to 4,294,967,295
- //  Int6 : Cardinal; //                        0 to 4,294,967,295
-#define LongInt int			//           -2,147,483,648 to 2,147,483,647
-#define Integer int  //           -2,147,483,648 to 2,147,483,647
-//#define Int64 long long		 // -9,223,372,036,854,775,808 to 9,223,372,036,854,775,807
-
-//#define Byte unsigned char		//                  0 to 255
-#define word unsigned short	//                        0 to 65,535
-#define smallint short 		//                  -32,768 to 32,767
-#define longword unsigned int	//                        0 to 4,294,967,295
- //  Int6 : Cardinal; //                        0 to 4,294,967,295
-#define longint int			//           -2,147,483,648 to 2,147,483,647
-#define integer int  //           -2,147,483,648 to 2,147,483,647
-
-typedef unsigned long ULONG;
-
-#define UCHAR unsigned char
-#define UINT unsigned int
-#define BOOL int
-#define TRUE 1
-#define FALSE 0
-
-// Soundcard Channels
-
-#define NONE 0
-#define LEFT 1
-#define RIGHT 2
-
-#define nr_emph 2
-
-#define decodedNormal 4 //'|'
-#define decodedFEC    3 //'F'
-#define decodedMEM	  2 //'#'
-#define decodedSingle 1 //'$'
-
-
-// Seems to use Delphi TStringList for a lot of queues. This seems to be a list of pointers and a count
-// Each pointer is to a Data/Length pair
-//Maybe something like
-
-typedef struct string_T
-{
-	unsigned char * Data;
-	int Length;
-	int AllocatedLength;				// A reasonable sized block is allocated at the start to speed up adding chars
-
-}string;
-
-typedef struct TStringList_T
-{
-	int Count;
-	string ** Items;
-
-} TStringList;
-
-// QPSK struct
-
-typedef struct TQPSK_t
-{
-	UCHAR tx[4];
-	int count[4];
-	UCHAR rx[4];
-	UCHAR mode;
-} TPQSK;
-
-
-typedef struct TKISSMode_t
-{
-	string * data_in;
-	void * Socket;				// Used as a key
-
-	// Not sure what rest are used for. Seems to be one per channel
-
-	TStringList buffer[4];			// Outgoing Frames
-
-} TKISSMode;
-
-typedef struct  TMChannel_t
-{
-
-	single prev_LPF1I_buf[4096];
-	single prev_LPF1Q_buf[4096];
-	single prev_dLPFI_buf[4096];
-	single prev_dLPFQ_buf[4096];
-	single prev_AFCI_buf[4096];
-	single prev_AFCQ_buf[4096];
-	single AngleCorr;
-	single MUX_osc;
-	single AFC_IZ1;
-	single AFC_IZ2;
-	single AFC_QZ1;
-	single AFC_QZ2;
-	single AFC_bit_buf1I[1024];
-	single AFC_bit_buf1Q[1024];
-	single AFC_bit_buf2[1024];
-	single AFC_IIZ1;
-	single AFC_QQZ1;
-
-} TMChannel;
-
-typedef struct TFX25_t
-{
-	string  data;
-	Byte  status;
-	Byte  bit_cnt;
-	Byte  byte_rx;
-	unsigned long long tag;
-	Byte  size;
-	Byte  rs_size;
-	Byte size_cnt;
-} TFX25;
-
-
-
-typedef struct TDetector_t
-{
-	struct TFX25_t fx25[4];
-	TStringList	mem_ARQ_F_buf[5];
-	TStringList mem_ARQ_buf[5];
-	float pll_loop[5];
-	float last_sample[5];
-	UCHAR ones[5];
-	UCHAR zeros[5];
-	float bit_buf[5][1024];
-	float bit_buf1[5][1024];
-	UCHAR sample_cnt[5];
-	UCHAR last_bit[5];
-	float PSK_IZ1[5];
-	float PSK_QZ1[5];
-	float PkAmpI[5];
-	float PkAmpQ[5];
-	float PkAmp[5];
-	float PkAmpMax[5];
-	int newpkpos[5];
-	float AverageAmp[5];
-	float AngleCorr[5];
-	float MinAmp[5];
-	float MaxAmp[5];
-	float MUX3_osc[5];
-	float MUX3_1_osc[5];
-	float MUX3_2_osc[5];
-	float Preemphasis6[5];
-	float Preemphasis12[5];
-	float PSK_AGC[5];
-	float AGC[5];
-	float AGC1[5];
-	float AGC2[5];
-	float AGC3[5];
-	float AGC_max[5];
-	float AGC_min[5];
-	float AFC_IZ1[5];
-	float AFC_IZ2[5];
-	float AFC_QZ1[5];
-	float AFC_QZ2[5];
-
-	UCHAR last_rx_bit[5];
-	UCHAR bit_stream[5];
-	UCHAR byte_rx[5];
-	UCHAR bit_stuff_cnt[5];
-	UCHAR bit_cnt[5];
-	float bit_osc[5];
-	UCHAR frame_status[5];
-	string rx_data[5];
-	string FEC_rx_data[5];
-	//
-	UCHAR FEC_pol[5];
-	unsigned short FEC_err[5];
-	unsigned long long FEC_header1[5][2];
-	unsigned short FEC_blk_int[5];
-	unsigned short FEC_len_int[5];
-	unsigned short FEC_len[5];
-
-	unsigned short FEC_len_cnt[5];
-	
-	UCHAR rx_intv_tbl[5][4];
-	UCHAR rx_intv_sym[5];
-	UCHAR rx_viterbi[5];
-	UCHAR viterbi_cnt[5];
-	//	  SurvivorStates [1..4,0..511] of TSurvivor;
-		  //
-	TMChannel MChannel[5][4];
-
-	float AFC_dF_avg[5];
-	float AFC_dF[5];
-	float AFC_bit_osc[5];
-	float AFC_bit_buf[5][1024];
-	unsigned short AFC_cnt[5];
-
-	string raw_bits1[5];
-	string raw_bits[5];
-	UCHAR last_nrzi_bit[5];
-
-	float BPF_core[5][2048];
-	float LPF_core[5][2048];
-
-	float src_INTR_buf[5][8192];
-	float src_INTRI_buf[5][8192];
-	float src_INTRQ_buf[5][8192];
-	float src_LPF1I_buf[5][8192];
-	float src_LPF1Q_buf[5][8192];
-
-	float src_BPF_buf[5][2048];
-	float src_Loop_buf[5][8192];
-	float prev_BPF_buf[5][4096];
-
-	float prev_LPF1I_buf[5][4096];
-	float prev_LPF1Q_buf[5][4096];
-	float prev_INTR_buf[5][16384];
-	float prev_INTRI_buf[5][16384];
-	float prev_INTRQ_buf[5][16384];
-
-	Byte emph_decoded;	
-	Byte rx_decoded;
-
-
-} TDetector;
-
-
-
-typedef struct AGWUser_t
-{
-	void *socket;
-	string * data_in;
-	TStringList AGW_frame_buf;
-	boolean	Monitor;
-	boolean	Monitor_raw;
-	boolean reportFreqAndModem;			// Can report modem and frequency to host
-
-} AGWUser;
-
-typedef struct  TAX25Info_t
-{
-	longint	stat_s_pkt;
-	longint stat_s_byte;
-	longint stat_r_pkt;
-	longint stat_r_byte;
-	longint stat_r_fc;
-	longint stat_fec_count;
-	time_t stat_begin_ses;
-	time_t stat_end_ses;
-	longint stat_l_r_byte;
-	longint stat_l_s_byte;
-
-} TAX25Info;
-
-typedef struct TAX25Port_t
-{
-	Byte hi_vs;
-	Byte vs;
-	Byte vr;
-	Byte PID;
-	TStringList in_data_buf;
-	TStringList frm_collector;
-	string frm_win[8];
-	string out_data_buf;
-	word t1;
-	word t2;
-	word t3;
-	Byte i_lo;
-	Byte i_hi;
-	word n1;
-	word n2;
-	word IPOLL_cnt;
-	TStringList frame_buf; //����� ������ �� ��������
-	TStringList I_frame_buf;
-	Byte status;
-	word clk_frack;
-	char corrcall[10];
-	char mycall[10];
-	UCHAR digi[56];
-	UCHAR Path[80];				// Path in ax25 format - added to save building it each time
-	UCHAR ReversePath[80];
-	int snd_ch;					// Simplifies parameter passing
-	int port;
-	int pathLen;
-	void * socket;
-	char kind[16];
-	TAX25Info info;
-} TAX25Port;
-
-
-#define LOGEMERGENCY 0 
-#define LOGALERT 1
-#define LOGCRIT 2 
-#define LOGERROR 3 
-#define LOGWARNING 4
-#define LOGNOTICE 5
-#define LOGINFO 6
-#define LOGDEBUG 7
-
-#define PTTRTS		1
-#define PTTDTR		2
-#define PTTCAT		4
-#define PTTCM108	8
-#define PTTHAMLIB	16
-
-// Status flags
-
-#define STAT_NO_LINK  0
-#define STAT_LINK 1
-#define STAT_CHK_LINK 2
-#define STAT_WAIT_ANS 3
-#define STAT_TRY_LINK 4
-#define STAT_TRY_UNLINK 5
-
-
-	// �md,Resp,Poll,Final,Digipeater flags
-#define 	SET_P 1
-#define 	SET_F 0
-#define 	SET_C 1
-#define 	SET_R 0
-#define 	SET_NO_RPT 0
-#define 	SET_RPT 1
-	// Frame ID flags
-#define 	I_FRM 0
-#define 	S_FRM 1
-#define 	U_FRM 2
-#define 	I_I 0
-#define 	S_RR 1
-#define 	S_RNR 5
-#define 	S_REJ 9
-#define		S_SREJ 0x0D
-#define 	U_SABM 47
-#define 	U_DISC 67
-#define 	U_DM 15
-#define 	U_UA 99
-#define 	U_FRMR 135
-#define 	U_UI 3
-	// PID flags
-#define 	PID_X25 0x01       // 00000001-CCIT X25 PLP
-#define 	PID_SEGMENT 0x08   // 00001000-Segmentation fragment
-#define 	PID_TEXNET 0xC3    // 11000011-TEXNET Datagram Protocol
-#define 	PID_LQ 0xC4        // 11001000-Link Quality Protocol
-#define 	PID_APPLETALK 0xCA // 11001010-Appletalk
-#define 	PID_APPLEARP 0xCB  // 11001011-Appletalk ARP
-#define 	PID_IP 0xCC        // 11001100-ARPA Internet Protocol
-#define 	PID_ARP 0xCD       // 11001101-ARPA Address Resolution Protocol
-#define 	PID_NET_ROM 0xCF   // 11001111-NET/ROM
-
-
-//	Sound interface buffer size
-
-#define SendSize 1024		// 100 mS for now
-#define ReceiveSize 512	// try 100 mS for now
-#define NumberofinBuffers 4
-
-#define Now getTicks()
-
-// #defines from all modules (?? is this a good idaa ??
-
-#define WIN_MAXIMIZED 0
-#define WIN_MINIMIZED 1
-#define MODEM_CAPTION 'SoundModem by UZ7HO'
-#define MODEM_VERSION '1.06'
-#define SND_IDLE 0
-#define SND_RX 1
-#define SND_TX 2
-#define BUF_EMPTY 0
-#define BUF_FULL 1
-#define DISP_MONO FALSE
-#define DISP_RGB TRUE
-#define MOD_IDLE 0
-#define MOD_RX 1
-#define MOD_TX 2
-#define MOD_WAIT 3
-#define TIMER_FREE 0
-#define TIMER_BUSY 1
-#define TIMER_OFF 2
-#define TIMER_EVENT_ON 3
-#define TIMER_EVENT_OFF 4
-#define DEBUG_TIMER 1
-#define DEBUG_WATERFALL 2
-#define DEBUG_DECODE 4
-#define DEBUG_SOUND 8
-#define IS_LAST TRUE
-#define IS_NOT_LAST FALSE
-#define modes_count 16
-#define SPEED_300 0
-#define SPEED_1200 1
-#define SPEED_600 2
-#define SPEED_2400 3
-#define SPEED_P1200 4
-#define SPEED_P600 5
-#define SPEED_P300 6
-#define SPEED_P2400 7
-#define SPEED_Q4800 8
-#define SPEED_Q3600 9
-#define SPEED_Q2400 10
-#define SPEED_MP400 11
-#define SPEED_DW2400 12
-#define SPEED_8P4800 13
-#define SPEED_AE2400 14
-#define SPEED_ARDOP 15
-
-#define MODE_FSK 0
-#define MODE_BPSK 1
-#define MODE_QPSK 2
-#define MODE_MPSK 3
-#define MODE_8PSK 4
-#define MODE_PI4QPSK 5
-#define MODE_ARDOP 6
-
-#define QPSK_SM 0
-#define QPSK_V26 1
-
-
-#define MODEM_8P4800_BPF 3200
-#define MODEM_8P4800_TXBPF 3400
-#define MODEM_8P4800_LPF 1000
-#define MODEM_8P4800_BPF_TAP 64
-#define MODEM_8P4800_LPF_TAP 8
- //
-#define MODEM_MP400_BPF 775
-#define MODEM_MP400_TXBPF 850
-#define MODEM_MP400_LPF 70
-#define MODEM_MP400_BPF_TAP 256
-#define MODEM_MP400_LPF_TAP 128
- //
-#define MODEM_DW2400_BPF 2400
-#define MODEM_DW2400_TXBPF 2500
-#define MODEM_DW2400_LPF 900
-#define MODEM_DW2400_BPF_TAP 256 //256
-#define MODEM_DW2400_LPF_TAP 32  //128
- //
-#define MODEM_Q2400_BPF 2400
-#define MODEM_Q2400_TXBPF 2500
-#define MODEM_Q2400_LPF 900
-#define MODEM_Q2400_BPF_TAP 256 //256
-#define MODEM_Q2400_LPF_TAP 128  //128
- //
-#define MODEM_Q3600_BPF 3600
-#define MODEM_Q3600_TXBPF 3750
-#define MODEM_Q3600_LPF 1350
-#define MODEM_Q3600_BPF_TAP 256
-#define MODEM_Q3600_LPF_TAP 128
- //
-#define MODEM_Q4800_BPF 4800
-#define MODEM_Q4800_TXBPF 5000
-#define MODEM_Q4800_LPF 1800
-#define MODEM_Q4800_BPF_TAP 256
-#define MODEM_Q4800_LPF_TAP 128
- //
-#define MODEM_P2400_BPF 4800
-#define MODEM_P2400_TXBPF 5000
-#define MODEM_P2400_LPF 1800
-#define MODEM_P2400_BPF_TAP 256
-#define MODEM_P2400_LPF_TAP 128
- //
-#define MODEM_P1200_BPF 2400
-#define MODEM_P1200_TXBPF 2500
-#define MODEM_P1200_LPF 900
-#define MODEM_P1200_BPF_TAP 256
-#define MODEM_P1200_LPF_TAP 128
- //
-#define MODEM_P600_BPF 1200
-#define MODEM_P600_TXBPF 1250
-#define MODEM_P600_LPF 400
-#define MODEM_P600_BPF_TAP 256
-#define MODEM_P600_LPF_TAP 128
- //
-#define MODEM_P300_BPF 600
-#define MODEM_P300_TXBPF 625
-#define MODEM_P300_LPF 200
-#define MODEM_P300_BPF_TAP 256
-#define MODEM_P300_LPF_TAP 128
- //
-#define MODEM_300_BPF 500
-#define MODEM_300_TXBPF 500
-#define MODEM_300_LPF 155
-#define MODEM_300_BPF_TAP 256
-#define MODEM_300_LPF_TAP 128
- //
-#define MODEM_600_BPF 800
-#define MODEM_600_TXBPF 900
-#define MODEM_600_LPF 325
-#define MODEM_600_BPF_TAP 256
-#define MODEM_600_LPF_TAP 128
- //
-#define MODEM_1200_BPF 1400
-#define MODEM_1200_TXBPF 1600
-#define MODEM_1200_LPF 650
-#define MODEM_1200_BPF_TAP 256
-#define MODEM_1200_LPF_TAP 128
- //
-#define MODEM_2400_BPF 3200
-#define MODEM_2400_TXBPF 3200
-#define MODEM_2400_LPF 1400
-#define MODEM_2400_BPF_TAP 256
-#define MODEM_2400_LPF_TAP 128
-
-#define TX_SILENCE 0
-#define TX_DELAY 1
-#define TX_TAIL 2
-#define TX_NO_DATA 3
-#define TX_FRAME 4
-#define TX_WAIT_BPF 5
-
-
-#define FRAME_WAIT 0
-#define FRAME_LOAD 1
-#define RX_BIT0 0
-#define RX_BIT1 128
-#define DCD_WAIT_SLOT 0
-#define DCD_WAIT_PERSIST 1
-
-#define FX25_MODE_NONE  0
-#define FX25_MODE_RX  1
-#define FX25_MODE_TXRX 2
-#define FX25_TAG 0
-#define FX25_LOAD 1
-
-#define    MODE_OUR 0
-#define    MODE_OTHER 1
-#define    MODE_RETRY 2
-
-#define FRAME_FLAG 126		// 7e
-
-#define port_num 32		// ?? Max AGW sessions
-#define PKT_ERR 17		// Minimum packet size, bytes
-#define I_MAX 7			// Maximum number of packets
-
-
-	// externs for all modules
-
-#define ARDOPBufferSize 12000 * 100
-
-extern short ARDOPTXBuffer[4][12000 * 100];	// Enough to hold whole frame of samples
-
-extern int ARDOPTXLen[4];				// Length of frame
-extern int ARDOPTXPtr[4];				// Tx Pointer
-
-extern BOOL KISSServ;
-extern int KISSPort;
-
-extern BOOL AGWServ;
-extern int AGWPort;
-
-extern TStringList KISS_acked[];
-extern TStringList KISS_iacked[];
-
-extern TStringList all_frame_buf[5];
-
-extern unsigned short pkt_raw_min_len;
-extern int stat_r_mem;
-
-extern UCHAR diddles;
-
-extern int stdtones;
-extern int fullduplex;
-
-extern struct TQPSK_t qpsk_set[4];
-
-extern int NonAX25[5];
-
-extern short txtail[5];
-extern short txdelay[5];
-
-extern short modem_def[5];
-
-extern int emph_db[5];
-extern UCHAR emph_all[5];
-
-extern UCHAR modem_mode[5];
-
-extern UCHAR RCVR[5];
-extern int soundChannel[5];
-extern int modemtoSoundLR[4];
-
-extern short rx_freq[5];
-extern short rx_shift[5];
-extern short rx_baudrate[5];
-extern short rcvr_offset[5];
-
-extern int tx_hitoneraisedb[5];
-extern float tx_hitoneraise[5];
-
-
-extern UCHAR tx_status[5];
-extern float tx_freq[5];
-extern float tx_shift[5];
-extern unsigned short tx_baudrate[5];
-
-extern unsigned short bpf[5];
-extern unsigned short lpf[5];
-
-extern unsigned short txbpf[5];
-
-extern unsigned short  tx_BPF_tap[5];
-extern unsigned short  tx_BPF_timer[5];
-
-extern unsigned short  BPF_tap[5];
-extern unsigned short  LPF_tap[5];
-
-extern float tx_BPF_core[5][32768];
-extern float LPF_core[5][2048];
-
-extern UCHAR xData[256];
-extern UCHAR xEncoded[256];
-extern UCHAR xDecoded[256];
-
-extern float PI125;
-extern float PI375;
-extern float PI625;
-extern float PI875;
-extern 	float PI5;
-extern float PI25;
-extern float PI75;
-
-extern int max_frame_collector[4];
-extern boolean KISS_opt[4];
-
-#define MaxErrors 4
-
-extern BOOL MinOnStart;
-
-//RS TReedSolomon;
-//  Form1 TForm1;
-//  WaveFormat TWaveFormatEx;
-
-extern int UDPServ;
-extern long long udpServerSeqno;
-
-extern int Channels;
-extern int BitsPerSample;
-extern float TX_Samplerate;
-extern float RX_Samplerate;
-extern int RX_SR;
-extern int TX_SR;
-extern int RX_PPM;
-extern int TX_PPM;
-extern int tx_bufsize;
-extern int rx_bufsize;
-extern int tx_bufcount;
-extern int rx_bufcount;
-extern int fft_size;
-extern int  mouse_down[2];
-//UCHAR * RX_pBuf array[257];
-//  RX_header array[1..256] of TWaveHdr;
-//  TX_pBuf array[1..4,1..256] of pointer;
-//TX_header array[1..4,1..256] of TWaveHdr;
-extern UCHAR calib_mode[5];
-extern UCHAR snd_status[5];
-extern UCHAR buf_status[5];
-extern UCHAR tx_buf_num1[5];
-extern UCHAR tx_buf_num[5];
-extern int speed[5];
-extern int panels[6];
-
-extern float fft_window_arr[2048];
-//  fft_s,fft_d array[0..2047] of TComplex;
-extern short fft_buf[5][2048];
-extern UCHAR fft_disp[5][2048];
-//  bm array[1..4] of TBitMap;
-//  bm1,bm2,bm3 TBitMap;
-
-//  WaveInHandle hWaveIn;
-//  WaveOutHandle array[1..4] of hWaveOut;
-extern int RXBufferLength;
-
-// data1 PData16;
-
-extern int grid_time;
-extern int fft_mult;
-extern int fft_spd;
-extern int grid_timer;
-extern int stop_wf;
-extern int raduga;
-extern char snd_rx_device_name[32];
-extern char snd_tx_device_name[32];
-extern int snd_rx_device;
-extern int snd_tx_device;
-extern UCHAR mod_icon_status;
-extern UCHAR last_mod_icon_status;
-extern UCHAR icon_timer;
-//  TelIni TIniFile;
-extern char cur_dir[];
-//  TimerId1 cardinal;
-//  TimerId2 cardinal;
-extern UCHAR TimerStat1;
-extern UCHAR TimerStat2;
-extern int stat_log;
-
-extern char PTTPort[80];			// Port for Hardware PTT - may be same as control port.
-extern int PTTMode;
-extern int PTTBAUD ;
-
-extern char PTTOnString[128];
-extern char PTTOffString[128];
-
-extern UCHAR PTTOnCmd[64];
-extern UCHAR PTTOnCmdLen;
-
-extern UCHAR PTTOffCmd[64];
-extern UCHAR PTTOffCmdLen;
-
-extern int PTT_device;
-extern int RX_device;
-extern int TX_device;
-extern int TX_rotate;
-extern int UsingLeft;
-extern int UsingRight;
-extern int UsingBothChannels;
-extern int pttGPIOPin;
-extern int pttGPIOPinR;
-extern BOOL pttGPIOInvert;
-extern BOOL useGPIO;
-extern BOOL gotGPIO;
-extern int VID;
-extern int PID;
-extern char CM108Addr[80];
-extern int HamLibPort;
-extern char HamLibHost[];
-
-extern int SCO;
-extern int DualPTT;
-extern UCHAR  DebugMode;
-extern UCHAR TimerEvent;
-extern int nr_monitor_lines;
-extern int UTC_Tim;
-extern int MainPriority;
-//  MainThreadHandle THandle;
-extern UCHAR w_state;
-
-extern BOOL Firstwaterfall;
-extern BOOL Secondwaterfall;
-
-extern int dcd_threshold;
-extern int rxOffset;
-extern int chanOffset[4];
-
-extern boolean busy;
-extern boolean dcd[5];
-
-extern struct TKISSMode_t  KISS;
-
-extern boolean dyn_frack[4] ;
-extern Byte recovery[4];
-extern Byte users[4];
-
-extern int resptime[4];
-extern int slottime[4];
-extern int persist[4];
-extern int fracks[4];
-extern int frack_time[4];
-extern int idletime[4];
-extern int redtime[4];
-extern int IPOLL[4];
-extern int maxframe[4];
-extern int TXFrmMode[4];
-
-extern char MyDigiCall[4][512];
-extern char exclude_callsigns[4][512];
-extern char exclude_APRS_frm[4][512];
-
-extern TStringList  list_exclude_callsigns[4];
-extern TStringList list_exclude_APRS_frm[4];
-extern TStringList list_digi_callsigns[4];
-
-
-extern int SoundIsPlaying;
-extern int Capturing;
-
-extern struct TDetector_t  DET[nr_emph + 1][16];
-
-extern char CaptureDevice[80];
-extern char PlaybackDevice[80];
-
-extern TAX25Port AX25Port[4][port_num];
-
-extern int fx25_mode[4];
-
-extern int tx_fx25_size[4];
-extern int tx_fx25_size_cnt[4];
-extern int tx_fx25_mode[4];
-
-extern int SatelliteMode;
-
-// Function prototypes
-
-void KISS_send_ack(UCHAR port, string * data);
-void AGW_AX25_frame_analiz(int snd_ch, int RX, string * frame);
-void FIR_filter(float * src, unsigned short buf_size, unsigned short tap, float * core, float * dest, float * prev);
-void make_core_TXBPF(UCHAR snd_ch, float freq, float width);
-void OpenPTTPort();
-void ClosePTTPort();
-
-void RadioPTT(int snd_ch, BOOL PTTState);
-void put_frame(int snd_ch, string * frame, char * code, int  tx_stat, int excluded);
-void CloseCOMPort(int fd);
-void COMClearRTS(int fd);
-void COMClearDTR(int fd);
-unsigned int getTicks();
-char * ShortDateTime();
-void  write_ax25_info(TAX25Port * AX25Sess);
-void reverse_addr(Byte * path, Byte * revpath, int Len);
-string * get_mycall(string * path);
-TAX25Port * get_user_port_by_calls(int snd_ch, char *  CallFrom, char *  CallTo);
-TAX25Port * get_free_port(int snd_ch);
-void * in_list_incoming_mycall(Byte * path);
-boolean add_incoming_mycalls(void * socket, char * src_call);
-int get_addr(char * Calls, UCHAR * AXCalls);
-void reverse_addr(Byte * path, Byte * revpath, int Len);
-void set_link(TAX25Port * AX25Sess, UCHAR * axpath);
-void rst_timer(TAX25Port * AX25Sess);
-void set_unlink(TAX25Port * AX25Sess, Byte * path);
-unsigned short get_fcs(UCHAR * Data, unsigned short len);
-void KISSSendtoServer(void * sock, Byte * Msg, int Len);
-int ConvFromAX25(unsigned char * incall, char * outcall);
-BOOL ConvToAX25(char * callsign, unsigned char * ax25call);
-void Debugprintf(const char * format, ...);
-
-double pila(double x);
-
-void AGW_Raw_monitor(int snd_ch, string * data);
-
-// Dephi emulation functions
-
-string * Strings(TStringList * Q, int Index);
-void Clear(TStringList * Q);
-int Count(TStringList * List);
-
-string * newString();
-string * copy(string * Source, int StartChar, int Count);
-TStringList * newTStringList();
-
-void freeString(string * Msg);
-
-void initString(string * S);
-void initTStringList(TStringList* T);
-
-// Two delete() This is confusing!!
-// Not really - one acts on String, other TStringList
-
-void Delete(TStringList * Q, int Index);
-void mydelete(string * Source, int StartChar, int Count);
-
-void move(UCHAR * SourcePointer, UCHAR * DestinationPointer, int CopyCount);
-void fmove(float * SourcePointer, float * DestinationPointer, int CopyCount);
-
-void setlength(string * Msg, int Count);		// Set string length
-
-string * stringAdd(string * Msg, UCHAR * Chars, int Count);		// Extend string 
-
-void Assign(TStringList * to, TStringList * from);	// Duplicate from to to
-
-string * duplicateString(string * in);
-
-// This looks for a string in a stringlist. Returns inhex if found, otherwise -1
-
-int  my_indexof(TStringList * l, string * s);
-
-boolean compareStrings(string * a, string * b);
-
-int Add(TStringList * Q, string * Entry);
-#ifdef __cplusplus
-}
-#endif
\ No newline at end of file
diff --git a/UZ7HOStuff.h b/UZ7HOStuff.h
index 47c7f60..00aa2f3 100644
--- a/UZ7HOStuff.h
+++ b/UZ7HOStuff.h
@@ -4,8 +4,8 @@
 //	 My port of UZ7HO's Soundmodem
 //
 
-#define VersionString "0.0.0.69"
-#define VersionBytes {0, 0, 0, 69}
+#define VersionString "0.0.0.70"
+#define VersionBytes {0, 0, 0, 70}
 
 // Added FX25. 4x100 FEC and V27 not Working and disabled
 
@@ -172,6 +172,8 @@
 //		Only display session table if AGW interface is enabled
 //		Fix operation with both left and right channels in use
 
+// .70  Restructure Waterfall area to be a single image 
+
 
 
 #include <string.h>
@@ -1129,6 +1131,7 @@ struct il2p_context_s {
 	int corrected;		// Number of symbols corrected by RS FEC.
 };
 
+extern int NeedWaterfallHeaders;
 
 #ifdef __cplusplus
 }
diff --git a/UZ7HOStuff.h.bak b/UZ7HOStuff.h.bak
deleted file mode 100644
index b7e5ec8..0000000
--- a/UZ7HOStuff.h.bak
+++ /dev/null
@@ -1,1049 +0,0 @@
-//
-//	 My port of UZ7HO's Soundmodem
-//
-
-#define VersionString "0.0.0.65"
-#define VersionBytes {0, 0, 0, 65}
-
-// Added FX25. 4x100 FEC and V27 not Working and disabled
-
-// 0.8 V27 now OK.
-
-// 0.9 Digipeating added
-
-// 0.10 Fix second channel tones and calibrate
-
-// 0.11 Fix allocation of sessions to correct modem
-//		Fix DCD
-//		Fix Monitoring of Multiline packets
-//		Fix possible saving of wrong center freq
-//		Limit TX sample Q in Linux
-//
-
-// 0.12	Add AGWPE monitoring of received frames
-//		Fix DCD Threshold
-//		Fix KISS transparency issue
-
-// 0.13 Fix sending last few bits in FX.25 Mode
-
-// 0.14 Add "Copy on Select" to Trace Window
-
-// 0.15 Limit Trace window to 10000 lines
-
-// 0.16 Fix overwriting monitor window after scrollback
-
-// 0.17	Add GPIO and CAT PTT
-
-// 0.18	Add CM108/119 PTT
-
-// 0.19 Fix scheduling KISS frames
-
-// 0.20 Debug code added to RR processing
-
-// 0.21	Fix AGW monitor of multiple line packets
-//		Close ax.25 sessions if AGW Host session closes
-
-// 0.22	Add FEC Count to Session Stats
-
-// 0.23 Retry DISC until UA received or retry count exceeded
-
-// 0.24	More fixes to DISC handling
-
-// 0.26 Add OSS PulseAudio and HAMLIB support
-
-// 0.27 Dynamically load PulseAudio modules
-
-// 0.28 Add ARDOPPacket Mode
-
-// 0.29 Fix saving settings and geometry on close
-// 0.30 Retructure code to build with Qt 5.3
-//      Fix crash in nogui mode if pulse requested but not available
-//		Try to fix memory leaks
-
-// 0.31 Add option to run modems in seprate threads
-
-// 0.32	Fix timing problem with AGW connect at startup
-//		Add Memory ARQ
-//		Add Single bit "Correction"
-//		Fix error in 31 when using multiple decoders
-
-// 0.33 Fix Single bit correction
-//		More memory leak fixes
-
-// 0.34 Add API to set Modem and Center Frequency
-//		Fix crash in delete_incoming_mycalls
-
-// 0.35 Return Version in AGW Extended g response
-
-// 0.36 Fix timing problem on startup
-
-// 0.37 Add scrollbars to Device and Modem dialogs
-
-// 0.38 Change default CM108 name to /dev/hidraw0 on Linux
-
-// 0.39	Dont try to display Message Boxes in nogui mode.
-//		Close Device and Modem dialogs on Accept or Reject
-//		Fix using HAMLIB in nogui mode
-
-// 0.40	Fix bug in frame optimize when using 6 char calls
-
-// 0.41	Fix "glitch" on waterfall markers when changing modem freqs 
-
-// 0.42	Add "Minimize to Tray" option
-
-// 0.43 Add Andy's on_SABM fix.
-//		Fix Crash if KISS Data sent to AGW port
-
-// 0.44 Add UDP bridge.
-
-// 0.45 Add two more modems.
-// 0.46 Fix two more modems.
-
-// 0.47 Fix suprious DM when host connection lost
-//		Add CWID
-
-// 0.48 Send FRMR for unrecognised frame types
-
-// 0.49 Add Andy's FEC Tag correlation coode
-
-// 0.50 Fix Waterfall display when only using right channel
-//		Allow 1200 baud fsk at other center freqs
-//		Add Port numbers to Window title and Try Icon tooltip
-//		Fix calculation of filters for multiple decoders
-//		Add RX Offset setting (for satellite operation
-
-// 0.51	Fix Multithreading with more that 2 modems
-
-// 0.52	Add Stdin as source on Linux
-
-// 0.53	Use Byte instead of byte as byte is defined in newer versions of gcc
-
-// 0.54 Fix for ALSA problem on new pi OS
-
-// 0.55 Fix for compiler error with newer compiler
-
-// 0.56	Fix errors in Config.cpp			June 22
-
-// 0.57	Add Restart Waterfall action		August 22
-
-// 0.58 Add RSID							Sept 2022
-
-// 0.59 Add config of Digi Calls			Dec 2022
-
-// 0.60 Allow ARDOP Packet on modems 2 to 4 March 2023
-
-// 0.61 Add il2p support					April 2023
-
-// 0.62										April 2023
-//	Add option to specify sound devices that aren't in list
-//	Add Save button to Modem dialog to save current tab without closing dialog
-//	Don't add plug: to Linux device addresses unless addr contains : (allows use of eg ARDOP)
-
-// 0.64 Fix sending ax.25 (broken in .61)
-
-// 0.65	Allow Set Modem command to use modem index as well as modem name
-
-
-
-#include <string.h>
-#include <stdlib.h>
-#include <math.h>
-#include <stdio.h>
-#include <ctype.h>
-#include <time.h>
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-#define UNUSED(x) (void)(x)
-
-#ifdef M_PI
-#undef M_PI
-#endif
-
-#define M_PI       3.1415926f
-
-#define pi M_PI
-
-#ifndef WIN32
-#define _strdup strdup
-#endif
-
-	//#define NULL ((void *)0)
-
-	//Delphi Types remember case insensitive
-
-#define single float
-#define boolean int
-#define Byte unsigned char		//                  0 to 255
-#define Word unsigned short	//                        0 to 65,535
-#define SmallInt short 		//                  -32,768 to 32,767
-#define LongWord unsigned int	//                        0 to 4,294,967,295
- //  Int6 : Cardinal; //                        0 to 4,294,967,295
-#define LongInt int			//           -2,147,483,648 to 2,147,483,647
-#define Integer int  //           -2,147,483,648 to 2,147,483,647
-//#define Int64 long long		 // -9,223,372,036,854,775,808 to 9,223,372,036,854,775,807
-
-//#define Byte unsigned char		//                  0 to 255
-#define word unsigned short	//                        0 to 65,535
-#define smallint short 		//                  -32,768 to 32,767
-#define longword unsigned int	//                        0 to 4,294,967,295
- //  Int6 : Cardinal; //                        0 to 4,294,967,295
-#define longint int			//           -2,147,483,648 to 2,147,483,647
-#define integer int  //           -2,147,483,648 to 2,147,483,647
-
-typedef unsigned long ULONG;
-
-#define UCHAR unsigned char
-#define UINT unsigned int
-#define BOOL int
-#define TRUE 1
-#define FALSE 0
-
-// Soundcard Channels
-
-#define NONE 0
-#define LEFT 1
-#define RIGHT 2
-
-#define nr_emph 2
-
-#define decodedNormal 4 //'-'
-#define decodedFEC    3 //'F'
-#define decodedMEM	  2 //'#'
-#define decodedSingle 1 //'$'
-
-
-// Seems to use Delphi TStringList for a lot of queues. This seems to be a list of pointers and a count
-// Each pointer is to a Data/Length pair
-//Maybe something like
-
-typedef struct string_T
-{
-	unsigned char * Data;
-	int Length;
-	int AllocatedLength;				// A reasonable sized block is allocated at the start to speed up adding chars
-
-}string;
-
-typedef struct TStringList_T
-{
-	int Count;
-	string ** Items;
-
-} TStringList;
-
-// QPSK struct
-
-typedef struct TQPSK_t
-{
-	UCHAR tx[4];
-	int count[4];
-	UCHAR rx[4];
-	UCHAR mode;
-} TPQSK;
-
-
-typedef struct TKISSMode_t
-{
-	string * data_in;
-	void * Socket;				// Used as a key
-
-	// Not sure what rest are used for. Seems to be one per channel
-
-	TStringList buffer[4];			// Outgoing Frames
-
-} TKISSMode;
-
-typedef struct  TMChannel_t
-{
-
-	single prev_LPF1I_buf[4096];
-	single prev_LPF1Q_buf[4096];
-	single prev_dLPFI_buf[4096];
-	single prev_dLPFQ_buf[4096];
-	single prev_AFCI_buf[4096];
-	single prev_AFCQ_buf[4096];
-	single AngleCorr;
-	single MUX_osc;
-	single AFC_IZ1;
-	single AFC_IZ2;
-	single AFC_QZ1;
-	single AFC_QZ2;
-	single AFC_bit_buf1I[1024];
-	single AFC_bit_buf1Q[1024];
-	single AFC_bit_buf2[1024];
-	single AFC_IIZ1;
-	single AFC_QQZ1;
-
-} TMChannel;
-
-typedef struct TFX25_t
-{
-	string  data;
-	Byte  status;
-	Byte  bit_cnt;
-	Byte  byte_rx;
-	unsigned long long tag;
-	Byte  size;
-	Byte  rs_size;
-	Byte size_cnt;
-} TFX25;
-
-
-
-typedef struct TDetector_t
-{
-	struct TFX25_t fx25[4];
-	TStringList	mem_ARQ_F_buf[5];
-	TStringList mem_ARQ_buf[5];
-	float pll_loop[5];
-	float last_sample[5];
-	UCHAR ones[5];
-	UCHAR zeros[5];
-	float bit_buf[5][1024];
-	float bit_buf1[5][1024];
-	UCHAR sample_cnt[5];
-	UCHAR last_bit[5];
-	float PSK_IZ1[5];
-	float PSK_QZ1[5];
-	float PkAmpI[5];
-	float PkAmpQ[5];
-	float PkAmp[5];
-	float PkAmpMax[5];
-	int newpkpos[5];
-	float AverageAmp[5];
-	float AngleCorr[5];
-	float MinAmp[5];
-	float MaxAmp[5];
-	float MUX3_osc[5];
-	float MUX3_1_osc[5];
-	float MUX3_2_osc[5];
-	float Preemphasis6[5];
-	float Preemphasis12[5];
-	float PSK_AGC[5];
-	float AGC[5];
-	float AGC1[5];
-	float AGC2[5];
-	float AGC3[5];
-	float AGC_max[5];
-	float AGC_min[5];
-	float AFC_IZ1[5];
-	float AFC_IZ2[5];
-	float AFC_QZ1[5];
-	float AFC_QZ2[5];
-
-	UCHAR last_rx_bit[5];
-	UCHAR bit_stream[5];
-	UCHAR byte_rx[5];
-	UCHAR bit_stuff_cnt[5];
-	UCHAR bit_cnt[5];
-	float bit_osc[5];
-	UCHAR frame_status[5];
-	string rx_data[5];
-	string FEC_rx_data[5];
-	//
-	UCHAR FEC_pol[5];
-	unsigned short FEC_err[5];
-	unsigned long long FEC_header1[5][2];
-	unsigned short FEC_blk_int[5];
-	unsigned short FEC_len_int[5];
-	unsigned short FEC_len[5];
-
-	unsigned short FEC_len_cnt[5];
-	
-	UCHAR rx_intv_tbl[5][4];
-	UCHAR rx_intv_sym[5];
-	UCHAR rx_viterbi[5];
-	UCHAR viterbi_cnt[5];
-	//	  SurvivorStates [1..4,0..511] of TSurvivor;
-		  //
-	TMChannel MChannel[5][4];
-
-	float AFC_dF_avg[5];
-	float AFC_dF[5];
-	float AFC_bit_osc[5];
-	float AFC_bit_buf[5][1024];
-	unsigned short AFC_cnt[5];
-
-	string raw_bits1[5];
-	string raw_bits[5];
-	UCHAR last_nrzi_bit[5];
-
-	float BPF_core[5][2048];
-	float LPF_core[5][2048];
-
-	float src_INTR_buf[5][8192];
-	float src_INTRI_buf[5][8192];
-	float src_INTRQ_buf[5][8192];
-	float src_LPF1I_buf[5][8192];
-	float src_LPF1Q_buf[5][8192];
-
-	float src_BPF_buf[5][2048];
-	float src_Loop_buf[5][8192];
-	float prev_BPF_buf[5][4096];
-
-	float prev_LPF1I_buf[5][4096];
-	float prev_LPF1Q_buf[5][4096];
-	float prev_INTR_buf[5][16384];
-	float prev_INTRI_buf[5][16384];
-	float prev_INTRQ_buf[5][16384];
-
-	Byte emph_decoded;	
-	Byte rx_decoded;
-	Byte errors;
-
-
-} TDetector;
-
-
-
-typedef struct AGWUser_t
-{
-	void *socket;
-	string * data_in;
-	TStringList AGW_frame_buf;
-	boolean	Monitor;
-	boolean	Monitor_raw;
-	boolean reportFreqAndModem;			// Can report modem and frequency to host
-
-} AGWUser;
-
-typedef struct  TAX25Info_t
-{
-	longint	stat_s_pkt;
-	longint stat_s_byte;
-	longint stat_r_pkt;
-	longint stat_r_byte;
-	longint stat_r_fc;
-	longint stat_fec_count;
-	time_t stat_begin_ses;
-	time_t stat_end_ses;
-	longint stat_l_r_byte;
-	longint stat_l_s_byte;
-
-} TAX25Info;
-
-typedef struct TAX25Port_t
-{
-	Byte hi_vs;
-	Byte vs;
-	Byte vr;
-	Byte PID;
-	TStringList in_data_buf;
-	TStringList frm_collector;
-	string frm_win[8];
-	string out_data_buf;
-	word t1;
-	word t2;
-	word t3;
-	Byte i_lo;
-	Byte i_hi;
-	word n1;
-	word n2;
-	word IPOLL_cnt;
-	TStringList frame_buf; //����� ������ �� ��������
-	TStringList I_frame_buf;
-	Byte status;
-	word clk_frack;
-	char corrcall[10];
-	char mycall[10];
-	UCHAR digi[56];
-	UCHAR Path[80];				// Path in ax25 format - added to save building it each time
-	UCHAR ReversePath[80];
-	int snd_ch;					// Simplifies parameter passing
-	int port;
-	int pathLen;
-	void * socket;
-	char kind[16];
-	TAX25Info info;
-} TAX25Port;
-
-
-#define LOGEMERGENCY 0 
-#define LOGALERT 1
-#define LOGCRIT 2 
-#define LOGERROR 3 
-#define LOGWARNING 4
-#define LOGNOTICE 5
-#define LOGINFO 6
-#define LOGDEBUG 7
-
-#define PTTRTS		1
-#define PTTDTR		2
-#define PTTCAT		4
-#define PTTCM108	8
-#define PTTHAMLIB	16
-
-// Status flags
-
-#define STAT_NO_LINK  0
-#define STAT_LINK 1
-#define STAT_CHK_LINK 2
-#define STAT_WAIT_ANS 3
-#define STAT_TRY_LINK 4
-#define STAT_TRY_UNLINK 5
-
-
-	// �md,Resp,Poll,Final,Digipeater flags
-#define 	SET_P 1
-#define 	SET_F 0
-#define 	SET_C 1
-#define 	SET_R 0
-#define 	SET_NO_RPT 0
-#define 	SET_RPT 1
-	// Frame ID flags
-#define 	I_FRM 0
-#define 	S_FRM 1
-#define 	U_FRM 2
-#define 	I_I 0
-#define 	S_RR 1
-#define 	S_RNR 5
-#define 	S_REJ 9
-#define		S_SREJ 0x0D
-#define 	U_SABM 47
-#define 	U_DISC 67
-#define 	U_DM 15
-#define 	U_UA 99
-#define 	U_FRMR 135
-#define 	U_UI 3
-	// PID flags
-#define 	PID_X25 0x01       // 00000001-CCIT X25 PLP
-#define 	PID_SEGMENT 0x08   // 00001000-Segmentation fragment
-#define 	PID_TEXNET 0xC3    // 11000011-TEXNET Datagram Protocol
-#define 	PID_LQ 0xC4        // 11001000-Link Quality Protocol
-#define 	PID_APPLETALK 0xCA // 11001010-Appletalk
-#define 	PID_APPLEARP 0xCB  // 11001011-Appletalk ARP
-#define 	PID_IP 0xCC        // 11001100-ARPA Internet Protocol
-#define 	PID_ARP 0xCD       // 11001101-ARPA Address Resolution Protocol
-#define 	PID_NET_ROM 0xCF   // 11001111-NET/ROM
-
-
-//	Sound interface buffer size
-
-#define SendSize 1024		// 100 mS for now
-#define ReceiveSize 512	// try 100 mS for now
-#define NumberofinBuffers 4
-
-#define Now getTicks()
-
-// #defines from all modules (?? is this a good idaa ??
-
-#define WIN_MAXIMIZED 0
-#define WIN_MINIMIZED 1
-#define MODEM_CAPTION 'SoundModem by UZ7HO'
-#define MODEM_VERSION '1.06'
-#define SND_IDLE 0
-#define SND_RX 1
-#define SND_TX 2
-#define BUF_EMPTY 0
-#define BUF_FULL 1
-#define DISP_MONO FALSE
-#define DISP_RGB TRUE
-#define MOD_IDLE 0
-#define MOD_RX 1
-#define MOD_TX 2
-#define MOD_WAIT 3
-#define TIMER_FREE 0
-#define TIMER_BUSY 1
-#define TIMER_OFF 2
-#define TIMER_EVENT_ON 3
-#define TIMER_EVENT_OFF 4
-#define DEBUG_TIMER 1
-#define DEBUG_WATERFALL 2
-#define DEBUG_DECODE 4
-#define DEBUG_SOUND 8
-#define IS_LAST TRUE
-#define IS_NOT_LAST FALSE
-#define modes_count 16
-#define SPEED_300 0
-#define SPEED_1200 1
-#define SPEED_600 2
-#define SPEED_2400 3
-#define SPEED_P1200 4
-#define SPEED_P600 5
-#define SPEED_P300 6
-#define SPEED_P2400 7
-#define SPEED_Q4800 8
-#define SPEED_Q3600 9
-#define SPEED_Q2400 10
-#define SPEED_MP400 11
-#define SPEED_DW2400 12
-#define SPEED_8P4800 13
-#define SPEED_AE2400 14
-#define SPEED_ARDOP 15
-
-#define MODE_FSK 0
-#define MODE_BPSK 1
-#define MODE_QPSK 2
-#define MODE_MPSK 3
-#define MODE_8PSK 4
-#define MODE_PI4QPSK 5
-#define MODE_ARDOP 6
-
-#define QPSK_SM 0
-#define QPSK_V26 1
-
-
-#define MODEM_8P4800_BPF 3200
-#define MODEM_8P4800_TXBPF 3400
-#define MODEM_8P4800_LPF 1000
-#define MODEM_8P4800_BPF_TAP 64
-#define MODEM_8P4800_LPF_TAP 8
- //
-#define MODEM_MP400_BPF 775
-#define MODEM_MP400_TXBPF 850
-#define MODEM_MP400_LPF 70
-#define MODEM_MP400_BPF_TAP 256
-#define MODEM_MP400_LPF_TAP 128
- //
-#define MODEM_DW2400_BPF 2400
-#define MODEM_DW2400_TXBPF 2500
-#define MODEM_DW2400_LPF 900
-#define MODEM_DW2400_BPF_TAP 256 //256
-#define MODEM_DW2400_LPF_TAP 32  //128
- //
-#define MODEM_Q2400_BPF 2400
-#define MODEM_Q2400_TXBPF 2500
-#define MODEM_Q2400_LPF 900
-#define MODEM_Q2400_BPF_TAP 256 //256
-#define MODEM_Q2400_LPF_TAP 128  //128
- //
-#define MODEM_Q3600_BPF 3600
-#define MODEM_Q3600_TXBPF 3750
-#define MODEM_Q3600_LPF 1350
-#define MODEM_Q3600_BPF_TAP 256
-#define MODEM_Q3600_LPF_TAP 128
- //
-#define MODEM_Q4800_BPF 4800
-#define MODEM_Q4800_TXBPF 5000
-#define MODEM_Q4800_LPF 1800
-#define MODEM_Q4800_BPF_TAP 256
-#define MODEM_Q4800_LPF_TAP 128
- //
-#define MODEM_P2400_BPF 4800
-#define MODEM_P2400_TXBPF 5000
-#define MODEM_P2400_LPF 1800
-#define MODEM_P2400_BPF_TAP 256
-#define MODEM_P2400_LPF_TAP 128
- //
-#define MODEM_P1200_BPF 2400
-#define MODEM_P1200_TXBPF 2500
-#define MODEM_P1200_LPF 900
-#define MODEM_P1200_BPF_TAP 256
-#define MODEM_P1200_LPF_TAP 128
- //
-#define MODEM_P600_BPF 1200
-#define MODEM_P600_TXBPF 1250
-#define MODEM_P600_LPF 400
-#define MODEM_P600_BPF_TAP 256
-#define MODEM_P600_LPF_TAP 128
- //
-#define MODEM_P300_BPF 600
-#define MODEM_P300_TXBPF 625
-#define MODEM_P300_LPF 200
-#define MODEM_P300_BPF_TAP 256
-#define MODEM_P300_LPF_TAP 128
- //
-#define MODEM_300_BPF 500
-#define MODEM_300_TXBPF 500
-#define MODEM_300_LPF 155
-#define MODEM_300_BPF_TAP 256
-#define MODEM_300_LPF_TAP 128
- //
-#define MODEM_600_BPF 800
-#define MODEM_600_TXBPF 900
-#define MODEM_600_LPF 325
-#define MODEM_600_BPF_TAP 256
-#define MODEM_600_LPF_TAP 128
- //
-#define MODEM_1200_BPF 1400
-#define MODEM_1200_TXBPF 1600
-#define MODEM_1200_LPF 650
-#define MODEM_1200_BPF_TAP 256
-#define MODEM_1200_LPF_TAP 128
- //
-#define MODEM_2400_BPF 3200
-#define MODEM_2400_TXBPF 3200
-#define MODEM_2400_LPF 1400
-#define MODEM_2400_BPF_TAP 256
-#define MODEM_2400_LPF_TAP 128
-
-#define TX_SILENCE 0
-#define TX_DELAY 1
-#define TX_TAIL 2
-#define TX_NO_DATA 3
-#define TX_FRAME 4
-#define TX_WAIT_BPF 5
-
-
-#define FRAME_WAIT 0
-#define FRAME_LOAD 1
-#define RX_BIT0 0
-#define RX_BIT1 128
-#define DCD_WAIT_SLOT 0
-#define DCD_WAIT_PERSIST 1
-
-#define FX25_MODE_NONE  0
-#define FX25_MODE_RX  1
-#define FX25_MODE_TXRX 2
-#define FX25_TAG 0
-#define FX25_LOAD 1
-
-#define IL2P_MODE_NONE  0
-#define IL2P_MODE_RX  1				// RX il2p + HDLC
-#define IL2P_MODE_TXRX 2
-#define IL2P_MODE_ONLY 3			// RX only il2p, TX il2p
-
-
-#define    MODE_OUR 0
-#define    MODE_OTHER 1
-#define    MODE_RETRY 2
-
-#define FRAME_FLAG 126		// 7e
-
-#define port_num 32		// ?? Max AGW sessions
-#define PKT_ERR 17		// Minimum packet size, bytes
-#define I_MAX 7			// Maximum number of packets
-
-
-	// externs for all modules
-
-#define ARDOPBufferSize 12000 * 100
-
-extern short ARDOPTXBuffer[4][12000 * 100];	// Enough to hold whole frame of samples
-
-extern int ARDOPTXLen[4];				// Length of frame
-extern int ARDOPTXPtr[4];				// Tx Pointer
-
-extern BOOL KISSServ;
-extern int KISSPort;
-
-extern BOOL AGWServ;
-extern int AGWPort;
-
-extern TStringList KISS_acked[];
-extern TStringList KISS_iacked[];
-
-extern TStringList all_frame_buf[5];
-
-extern unsigned short pkt_raw_min_len;
-extern int stat_r_mem;
-
-extern UCHAR diddles;
-
-extern int stdtones;
-extern int fullduplex;
-
-extern struct TQPSK_t qpsk_set[4];
-
-extern int NonAX25[5];
-
-extern short txtail[5];
-extern short txdelay[5];
-
-extern short modem_def[5];
-
-extern int emph_db[5];
-extern UCHAR emph_all[5];
-
-extern UCHAR modem_mode[5];
-
-extern UCHAR RCVR[5];
-extern int soundChannel[5];
-extern int modemtoSoundLR[4];
-
-extern short rx_freq[5];
-extern short rx_shift[5];
-extern short rx_baudrate[5];
-extern short rcvr_offset[5];
-
-extern int tx_hitoneraisedb[5];
-extern float tx_hitoneraise[5];
-
-
-extern UCHAR tx_status[5];
-extern float tx_freq[5];
-extern float tx_shift[5];
-extern unsigned short tx_baudrate[5];
-
-extern unsigned short bpf[5];
-extern unsigned short lpf[5];
-
-extern unsigned short txbpf[5];
-
-extern unsigned short  tx_BPF_tap[5];
-extern unsigned short  tx_BPF_timer[5];
-
-extern unsigned short  BPF_tap[5];
-extern unsigned short  LPF_tap[5];
-
-extern float tx_BPF_core[5][32768];
-extern float LPF_core[5][2048];
-
-extern UCHAR xData[256];
-extern UCHAR xEncoded[256];
-extern UCHAR xDecoded[256];
-
-extern float PI125;
-extern float PI375;
-extern float PI625;
-extern float PI875;
-extern 	float PI5;
-extern float PI25;
-extern float PI75;
-
-extern int max_frame_collector[4];
-extern boolean KISS_opt[4];
-
-#define MaxErrors 4
-
-extern BOOL MinOnStart;
-
-//RS TReedSolomon;
-//  Form1 TForm1;
-//  WaveFormat TWaveFormatEx;
-
-extern int UDPServ;
-extern long long udpServerSeqno;
-
-extern int Channels;
-extern int BitsPerSample;
-extern float TX_Samplerate;
-extern float RX_Samplerate;
-extern int RX_SR;
-extern int TX_SR;
-extern int RX_PPM;
-extern int TX_PPM;
-extern int tx_bufsize;
-extern int rx_bufsize;
-extern int tx_bufcount;
-extern int rx_bufcount;
-extern int fft_size;
-extern int  mouse_down[2];
-//UCHAR * RX_pBuf array[257];
-//  RX_header array[1..256] of TWaveHdr;
-//  TX_pBuf array[1..4,1..256] of pointer;
-//TX_header array[1..4,1..256] of TWaveHdr;
-extern UCHAR calib_mode[5];
-extern UCHAR snd_status[5];
-extern UCHAR buf_status[5];
-extern UCHAR tx_buf_num1[5];
-extern UCHAR tx_buf_num[5];
-extern int speed[5];
-extern int panels[6];
-
-extern int FFTSize;
-#define fft_size FFTSize
-
-extern float fft_window_arr[2048];
-//  fft_s,fft_d array[0..2047] of TComplex;
-extern short fft_buf[5][4096];
-extern UCHAR fft_disp[5][4096];
-//  bm array[1..4] of TBitMap;
-//  bm1,bm2,bm3 TBitMap;
-
-//  WaveInHandle hWaveIn;
-//  WaveOutHandle array[1..4] of hWaveOut;
-extern int RXBufferLength;
-
-// data1 PData16;
-
-extern int grid_time;
-extern int fft_mult;
-extern int fft_spd;
-extern int grid_timer;
-extern int stop_wf;
-extern int raduga;
-extern char snd_rx_device_name[32];
-extern char snd_tx_device_name[32];
-extern int snd_rx_device;
-extern int snd_tx_device;
-extern UCHAR mod_icon_status;
-extern UCHAR last_mod_icon_status;
-extern UCHAR icon_timer;
-//  TelIni TIniFile;
-extern char cur_dir[];
-//  TimerId1 cardinal;
-//  TimerId2 cardinal;
-extern UCHAR TimerStat1;
-extern UCHAR TimerStat2;
-extern int stat_log;
-
-extern char PTTPort[80];			// Port for Hardware PTT - may be same as control port.
-extern int PTTMode;
-extern int PTTBAUD ;
-
-extern char PTTOnString[128];
-extern char PTTOffString[128];
-
-extern UCHAR PTTOnCmd[64];
-extern UCHAR PTTOnCmdLen;
-
-extern UCHAR PTTOffCmd[64];
-extern UCHAR PTTOffCmdLen;
-
-extern int PTT_device;
-extern int RX_device;
-extern int TX_device;
-extern int TX_rotate;
-extern int UsingLeft;
-extern int UsingRight;
-extern int UsingBothChannels;
-extern int pttGPIOPin;
-extern int pttGPIOPinR;
-extern BOOL pttGPIOInvert;
-extern BOOL useGPIO;
-extern BOOL gotGPIO;
-extern int VID;
-extern int PID;
-extern char CM108Addr[80];
-extern int HamLibPort;
-extern char HamLibHost[];
-
-extern int SCO;
-extern int DualPTT;
-extern UCHAR  DebugMode;
-extern UCHAR TimerEvent;
-extern int nr_monitor_lines;
-extern int UTC_Tim;
-extern int MainPriority;
-//  MainThreadHandle THandle;
-extern UCHAR w_state;
-
-extern BOOL Firstwaterfall;
-extern BOOL Secondwaterfall;
-
-extern int dcd_threshold;
-extern int rxOffset;
-extern int chanOffset[4];
-
-extern boolean busy;
-extern boolean dcd[5];
-
-extern struct TKISSMode_t  KISS;
-
-extern boolean dyn_frack[4] ;
-extern Byte recovery[4];
-extern Byte users[4];
-
-extern int resptime[4];
-extern int slottime[4];
-extern int persist[4];
-extern int fracks[4];
-extern int frack_time[4];
-extern int idletime[4];
-extern int redtime[4];
-extern int IPOLL[4];
-extern int maxframe[4];
-extern int TXFrmMode[4];
-
-extern char MyDigiCall[4][512];
-extern char exclude_callsigns[4][512];
-extern char exclude_APRS_frm[4][512];
-
-extern TStringList  list_exclude_callsigns[4];
-extern TStringList list_exclude_APRS_frm[4];
-extern TStringList list_digi_callsigns[4];
-
-
-extern int SoundIsPlaying;
-extern int Capturing;
-
-extern struct TDetector_t  DET[nr_emph + 1][16];
-
-extern char CaptureDevice[80];
-extern char PlaybackDevice[80];
-
-extern TAX25Port AX25Port[4][port_num];
-
-extern int fx25_mode[4];
-extern int il2p_mode[4];
-
-extern int tx_fx25_size[4];
-extern int tx_fx25_size_cnt[4];
-extern int tx_fx25_mode[4];
-
-extern int SatelliteMode;
-
-// Function prototypes
-
-void KISS_send_ack(UCHAR port, string * data);
-void AGW_AX25_frame_analiz(int snd_ch, int RX, string * frame);
-void FIR_filter(float * src, unsigned short buf_size, unsigned short tap, float * core, float * dest, float * prev);
-void make_core_TXBPF(UCHAR snd_ch, float freq, float width);
-void OpenPTTPort();
-void ClosePTTPort();
-
-void RadioPTT(int snd_ch, BOOL PTTState);
-void put_frame(int snd_ch, string * frame, char * code, int  tx_stat, int excluded);
-void CloseCOMPort(int fd);
-void COMClearRTS(int fd);
-void COMClearDTR(int fd);
-unsigned int getTicks();
-char * ShortDateTime();
-void  write_ax25_info(TAX25Port * AX25Sess);
-void reverse_addr(Byte * path, Byte * revpath, int Len);
-string * get_mycall(string * path);
-TAX25Port * get_user_port_by_calls(int snd_ch, char *  CallFrom, char *  CallTo);
-TAX25Port * get_free_port(int snd_ch);
-void * in_list_incoming_mycall(Byte * path);
-boolean add_incoming_mycalls(void * socket, char * src_call);
-int get_addr(char * Calls, UCHAR * AXCalls);
-void reverse_addr(Byte * path, Byte * revpath, int Len);
-void set_link(TAX25Port * AX25Sess, UCHAR * axpath);
-void rst_timer(TAX25Port * AX25Sess);
-void set_unlink(TAX25Port * AX25Sess, Byte * path);
-unsigned short get_fcs(UCHAR * Data, unsigned short len);
-void KISSSendtoServer(void * sock, Byte * Msg, int Len);
-int ConvFromAX25(unsigned char * incall, char * outcall);
-BOOL ConvToAX25(char * callsign, unsigned char * ax25call);
-void Debugprintf(const char * format, ...);
-
-double pila(double x);
-
-void AGW_Raw_monitor(int snd_ch, string * data);
-
-// Dephi emulation functions
-
-string * Strings(TStringList * Q, int Index);
-void Clear(TStringList * Q);
-int Count(TStringList * List);
-
-string * newString();
-string * copy(string * Source, int StartChar, int Count);
-TStringList * newTStringList();
-
-void freeString(string * Msg);
-
-void initString(string * S);
-void initTStringList(TStringList* T);
-
-// Two delete() This is confusing!!
-// Not really - one acts on String, other TStringList
-
-void Delete(TStringList * Q, int Index);
-void mydelete(string * Source, int StartChar, int Count);
-
-void move(UCHAR * SourcePointer, UCHAR * DestinationPointer, int CopyCount);
-void fmove(float * SourcePointer, float * DestinationPointer, int CopyCount);
-
-void setlength(string * Msg, int Count);		// Set string length
-
-string * stringAdd(string * Msg, UCHAR * Chars, int Count);		// Extend string 
-
-void Assign(TStringList * to, TStringList * from);	// Duplicate from to to
-
-string * duplicateString(string * in);
-
-// This looks for a string in a stringlist. Returns inhex if found, otherwise -1
-
-int  my_indexof(TStringList * l, string * s);
-
-boolean compareStrings(string * a, string * b);
-
-int Add(TStringList * Q, string * Entry);
-#ifdef __cplusplus
-}
-#endif
\ No newline at end of file
diff --git a/agwlib.h b/agwlib.h
deleted file mode 100644
index 688f918..0000000
--- a/agwlib.h
+++ /dev/null
@@ -1,45 +0,0 @@
-
-#ifndef AGWLIB_H
-#define AGWLIB_H 1
-
-
-// Call at beginning to start it up.
-
-int agwlib_init (char *host, char *port, int (*init_func)(void));
-
-
-
-// Send commands to TNC.
-
-
-int agwlib_X_register_callsign (int chan, char *call_from);
-
-int agwlib_x_unregister_callsign (int chan, char *call_from);
-
-int agwlib_G_ask_port_information (void);
-
-int agwlib_C_connect (int chan, char *call_from, char *call_to);
-
-int agwlib_d_disconnect (int chan, char *call_from, char *call_to);
-
-int agwlib_D_send_connected_data (int chan, int pid, char *call_from, char *call_to, int data_len, char *data);
-
-int agwlib_Y_outstanding_frames_for_station (int chan, char *call_from, char *call_to);
-
-
-
-// The application must define these.
-
-void agw_cb_C_connection_received (int chan, char *call_from, char *call_to, int data_len, char *data);
-void on_C_connection_received (int chan, char *call_from, char *call_to, int incoming, char *data);
-
-void agw_cb_d_disconnected (int chan, char *call_from, char *call_to, int data_len, char *data);
-
-void agw_cb_D_connected_data (int chan, char *call_from, char *call_to, int data_len, char *data);
-
-void agw_cb_G_port_information (int num_chan, char *chan_descriptions[]);
-
-void agw_cb_Y_outstanding_frames_for_station (int chan, char *call_from, char *call_to, int frame_count);
-
-
-#endif
\ No newline at end of file
diff --git a/ais.h b/ais.h
deleted file mode 100644
index 6b96288..0000000
--- a/ais.h
+++ /dev/null
@@ -1,8 +0,0 @@
-
-
-void ais_to_nmea (unsigned char *ais, int ais_len, char *nema, int nema_size);
-
-int ais_parse (char *sentence, int quiet, char *descr, int descr_size, char *mssi, int mssi_size, double *odlat, double *odlon,
-			float *ofknots, float *ofcourse, float *ofalt_m, char *symtab, char *symbol, char *comment, int comment_size);
-
-int ais_check_length (int type, int length);
diff --git a/aprs_tt.h b/aprs_tt.h
deleted file mode 100644
index 4d33f48..0000000
--- a/aprs_tt.h
+++ /dev/null
@@ -1,191 +0,0 @@
-
-/* aprs_tt.h */
-
-#ifndef APRS_TT_H
-#define APRS_TT_H 1
-
-
-
-/*
- * For holding location format specifications from config file.
- * Same thing is also useful for macro definitions.
- * We have exactly the same situation of looking for a pattern
- * match and extracting fixed size groups of digits.
- */
-
-struct ttloc_s {
-	enum { TTLOC_POINT, TTLOC_VECTOR, TTLOC_GRID, TTLOC_UTM, TTLOC_MGRS, TTLOC_USNG, TTLOC_MACRO, TTLOC_MHEAD, TTLOC_SATSQ, TTLOC_AMBIG } type;
-
-	char pattern[20];	/* e.g. B998, B5bbbdddd, B2xxyy, Byyyxxx, BAxxxx */
-				/* For macros, it should be all fixed digits, */
-				/* and the letters x, y, z.  e.g.  911, xxyyyz */
-
-	union {
-
-	  struct {	
-	    double lat;		/* Specific locations. */
-	    double lon;
-	  } point;
-
-	  struct {
-	    double lat;		/* For bearing/direction. */
-	    double lon;
-	    double scale;	/* conversion to meters */
-	  } vector;
-
-	  struct {
-	    double lat0;	/* yyy all zeros. */
-	    double lon0;	/* xxx */
-	    double lat9;	/* yyy all nines. */
-	    double lon9;	/* xxx */
-	  } grid;
-
-	  struct {
-	    double scale;
-	    double x_offset;
-	    double y_offset;
-	    long lzone;		/* UTM zone, should be 1-60 */
-	    char latband;	/* Latitude band if specified, otherwise space or - */
-	    char hemi;		/* UTM Hemisphere, should be 'N' or 'S'. */
-	  } utm;
-
-	  struct {
-	    char zone[8];	/* Zone and square for USNG/MGRS */
-	  } mgrs;
-
-	  struct {
-	    char prefix[24];	/* should be 10, 6, or 4 digits to be */
-				/* prepended to the received sequence. */
-	  } mhead;
-
-	  struct {
-	    char *definition;
-	  } macro;
-
-	};
-};
-
-
-/* Error codes for sending responses to user. */
-
-#define TT_ERROR_OK		0	/* Success. */
-#define TT_ERROR_D_MSG		1	/* D was first char of field.  Not implemented yet. */
-#define TT_ERROR_INTERNAL	2	/* Internal error.  Shouldn't be here. */
-#define TT_ERROR_MACRO_NOMATCH	3	/* No definition for digit sequence. */
-#define TT_ERROR_BAD_CHECKSUM	4	/* Bad checksum on call. */
-#define TT_ERROR_INVALID_CALL	5	/* Invalid callsign. */
-#define TT_ERROR_INVALID_OBJNAME 6	/* Invalid object name. */
-#define TT_ERROR_INVALID_SYMBOL	7	/* Invalid symbol specification. */
-#define TT_ERROR_INVALID_LOC	8	/* Invalid location. */
-#define TT_ERROR_NO_CALL	9	/* No call or object name included. */
-#define TT_ERROR_INVALID_MHEAD	10	/* Invalid Maidenhead Locator. */
-#define TT_ERROR_INVALID_SATSQ	11	/* Satellite square must be 4 digits. */
-#define TT_ERROR_SUFFIX_NO_CALL 12	/* No known callsign for suffix. */
-
-#define TT_ERROR_MAXP1		13	/* Number of items above.  i.e. Last number plus 1. */
-
-
-#if CONFIG_C		/* Is this being included from config.c? */
-
-/* Must keep in sync with above !!! */
-
-static const char *tt_msg_id[TT_ERROR_MAXP1] = {
-	"OK",
-	"D_MSG",
-	"INTERNAL",
-	"MACRO_NOMATCH",
-	"BAD_CHECKSUM",
-	"INVALID_CALL",
-	"INVALID_OBJNAME",
-	"INVALID_SYMBOL",
-	"INVALID_LOC",
-	"NO_CALL",
-	"INVALID_MHEAD",
-	"INVALID_SATSQ",
-	"SUFFIX_NO_CALL"
-};
-
-#endif
-
-/* 
- * Configuration options for APRStt.
- */
-
-#define TT_MAX_XMITS 10
-
-#define TT_MTEXT_LEN 64
-
-
-struct tt_config_s {
-
-	int gateway_enabled;		/* Send DTMF sequences to APRStt gateway. */
-
-	int obj_recv_chan;		/* Channel to listen for tones. */
-
-	int obj_xmit_chan;		/* Channel to transmit object report. */
-					/* -1 for none.  This could happen if we */
-					/* are only sending to application */
-					/* and/or IGate. */
-
-	int obj_send_to_app;		/* send to attached application(s). */
-
-	int obj_send_to_ig;		/* send to IGate. */
-
-	char obj_xmit_via[AX25_MAX_REPEATERS * (AX25_MAX_ADDR_LEN+1)];	
-					/* e.g.  empty or "WIDE2-1,WIDE1-1" */
-	
-	int retain_time;		/* Seconds to keep information about a user. */
-
-	int num_xmits;			/* Number of times to transmit object report. */
-				
-	int xmit_delay[TT_MAX_XMITS];	/* Delay between them. */
-					/* e.g.  3 seconds before first transmission then */
-					/* delays of 16, 32, seconds etc. in between repeats. */
-
-	struct ttloc_s *ttloc_ptr;	/* Pointer to variable length array of above. */
-	int ttloc_size;			/* Number of elements allocated. */
-	int ttloc_len;			/* Number of elements actually used. */
-
-	double corral_lat;		/* The "corral" for unknown locations. */
-	double corral_lon;
-	double corral_offset;
-	int corral_ambiguity;
-
-	char status[10][TT_MTEXT_LEN];		/* Up to 9 status messages. e.g.  "/enroute" */
-						/* Position 0 means none and can't be changed. */
-
-	struct {
-	  char method[AX25_MAX_ADDR_LEN];	/* SPEECH or MORSE[-n] */
-	  char mtext[TT_MTEXT_LEN];		/* Message text. */
-	} response[TT_ERROR_MAXP1];
-
-	char ttcmd[80];			/* Command to generate custom audible response. */
-};
-
-
-
-	
-void aprs_tt_init (struct tt_config_s *p_config, int debug);
-
-void aprs_tt_button (int chan, char button);
-
-
-
-
-
-#define APRSTT_LOC_DESC_LEN 32		/* Need at least 26 */
-
-#define APRSTT_DEFAULT_SYMTAB '\\'
-#define APRSTT_DEFAULT_SYMBOL 'A'
-
-
-void aprs_tt_dao_to_desc (char *dao, char *str);
-
-void aprs_tt_sequence (int chan, char *msg);
-
-int dw_run_cmd (char *cmd, int oneline, char *result, size_t resultsiz);
-
-
-#endif
-
-/* end aprs_tt.h */
\ No newline at end of file
diff --git a/audio_stats.h b/audio_stats.h
deleted file mode 100644
index 4cf8ad0..0000000
--- a/audio_stats.h
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
-/* audio_stats.h */
-
-
-extern void audio_stats (int adev, int nchan, int nsamp, int interval);
-
diff --git a/ax25_link.h b/ax25_link.h
deleted file mode 100644
index 40fa401..0000000
--- a/ax25_link.h
+++ /dev/null
@@ -1,88 +0,0 @@
-
-/* ax25_link.h */
-
-
-#ifndef AX25_LINK_H
-#define AX25_LINK_H 1
-
-#include "ax25_pad.h"		// for AX25_MAX_INFO_LEN
-
-#include "dlq.h"		// for dlq_item_t
-
-#include "config.h"		// for struct misc_config_s
-
-
-
-// Limits and defaults for parameters.
-
-
-#define AX25_N1_PACLEN_MIN 1		// Max bytes in Information part of frame.
-#define AX25_N1_PACLEN_DEFAULT 256	// some v2.0 implementations have 128
-#define AX25_N1_PACLEN_MAX AX25_MAX_INFO_LEN	// from ax25_pad.h
-
-
-#define AX25_N2_RETRY_MIN 1		// Number of times to retry before giving up.
-#define AX25_N2_RETRY_DEFAULT 10
-#define AX25_N2_RETRY_MAX 15
-
-
-#define AX25_T1V_FRACK_MIN 1		// Number of seconds to wait before retrying.
-#define AX25_T1V_FRACK_DEFAULT 3	// KPC-3+ has 4.  TM-D710A has 3.
-#define AX25_T1V_FRACK_MAX 15
-
-
-#define AX25_K_MAXFRAME_BASIC_MIN 1		// Window size - number of I frames to send before waiting for ack.
-#define AX25_K_MAXFRAME_BASIC_DEFAULT 4
-#define AX25_K_MAXFRAME_BASIC_MAX 7
-
-#define AX25_K_MAXFRAME_EXTENDED_MIN 1
-#define AX25_K_MAXFRAME_EXTENDED_DEFAULT 32
-#define AX25_K_MAXFRAME_EXTENDED_MAX 63		// In theory 127 but I'm restricting as explained in SREJ handling.
-
-
-
-// Call once at startup time.
-
-void ax25_link_init (struct misc_config_s *pconfig);
-
-
-
-// IMPORTANT:
-
-// These functions must be called on a single thread, one at a time.
-// The Data Link Queue (DLQ) is used to serialize events from multiple sources.
-
-// Maybe the dispatch switch should be moved to ax25_link.c so they can all
-// be made static and they can't be called from the wrong place accidentally.
-
-void dl_connect_request (dlq_item_t *E);
-
-void dl_disconnect_request (dlq_item_t *E);
-
-void dl_data_request (dlq_item_t *E);
-
-void dl_register_callsign (dlq_item_t *E);
-
-void dl_unregister_callsign (dlq_item_t *E);
-
-void dl_outstanding_frames_request (dlq_item_t *E);
-
-void dl_client_cleanup (dlq_item_t *E);
-
-
-void lm_data_indication (dlq_item_t *E);
-
-void lm_seize_confirm (dlq_item_t *E);
-
-void lm_channel_busy (dlq_item_t *E);
-
-
-void dl_timer_expiry (void);
-
-
-double ax25_link_get_next_timer_expiry (void);
-
-
-#endif
-
-/* end ax25_link.h */
\ No newline at end of file
diff --git a/ax25_mod-DESKTOP-MHE5LO8.c b/ax25_mod-DESKTOP-MHE5LO8.c
deleted file mode 100644
index 4c803c2..0000000
--- a/ax25_mod-DESKTOP-MHE5LO8.c
+++ /dev/null
@@ -1,1810 +0,0 @@
-/*
-Copyright (C) 2019-2020 Andrei Kopanchuk UZ7HO
-
-This file is part of QtSoundModem
-
-QtSoundModem is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-QtSoundModem is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with QtSoundModem.  If not, see http://www.gnu.org/licenses
-
-*/
-
-// UZ7HO Soundmodem Port by John Wiseman G8BPQ
-
-
-#include "UZ7HOStuff.h"
-
-// I assume this modulates (and sends?} frames
-
-int RSEncode(UCHAR * bytToRS, UCHAR * RSBytes, int DataLen, int RSLen);
-
-//unit ax25_mod;
-
-//interface
-
-//uses sysutils,classes,math
-
-extern int SampleNo;
-
-extern BOOL KISSServ;
-
-extern TStringList KISS_acked[];
-extern TStringList KISS_iacked[];
-
-extern UCHAR modem_mode[];
-
-#define sbc 175
-
-extern single  ch_offset[4];
-int Continuation[4] = { 0, 0, 0, 0 };	// Sending 2nd or more packet of burst
-
-#define COS45 0.70710676908493f
-
-#define TX_SILENCE 0
-#define TX_DELAY 1
-#define TX_TAIL 2
-#define TX_NO_DATA 3
-#define TX_FRAME 4
-#define TX_WAIT_BPF 5
-
-
-#define TX_BIT0 0
-#define TX_BIT1 1
-#define FRAME_EMPTY 0
-#define FRAME_FULL 1
-#define FRAME_NO_FRAME 2
-#define FRAME_NEW_FRAME 3
-#define BYTE_EMPTY 0
-#define BYTE_FULL 1
-
-
-UCHAR gray_8PSK[8] = {7,0,6,5,2,1,3,4};		// ?? was 1::8
-
-UCHAR gray_PI4QPSK[4] = {3,1,5,7};
-
-
-float audio_buf[5][32768];  // [1..4,0..32767]
-float tx_src_BPF_buf[5][32768];
-float tx_BPF_buf[5][32768];
-float tx_prev_BPF_buf[5][32768];
-float tx_BPF_core[5][32768];
-
-long tx_delay_cnt[5] = {0};		//			 : array[1..4] of longword=(0,0,0,0};
-long tx_tail_cnt[5] = {0};
-
-int tx_hitoneraisedb[5] = {0};		//   : array[1..4] of integer=(0,0,0,0};
-float tx_hitoneraise[5] = {0};		//     : array[1..4] of single=(0,0,0,0};
-float tx_freq[5] = { 1000, 1000, 1000, 1000, 1000};			//			     : array[1..4] of single=(1000,1000,1000,1000};
-float tx_shift[5] = { 200, 200, 200, 200, 200};				  //   : array[1..4] of single=(200,200,200,200};
-float tx_bit_mod[5] = {1, 1, 1, 1, 1};		//			   : array[1..4] of single=(1,1,1,1};
-float tx_osc[5] = {0};		//						 : array[1..4] of single=(0,0,0,0};
-float tx_bit_osc[5] = {0};		//			   : array[1..4] of single=(0,0,0,0};
-unsigned short txbpf[5] = { 400, 400, 400, 400, 400};		//						  : array[1..4] of word=(400,400,400,400};
-unsigned short  tx_BPF_tap[5] = { 256, 256, 256, 256, 256};		//			   : array[1..4] of word=(256,256,256,256};
-unsigned short  tx_baudrate[5] = { 300, 300, 300, 300, 300 };		//			  : array[1..4] of word=(300,300,300,300};
-unsigned short  tx_bitrate[5] = { 300, 300, 300, 300, 300 };		//			  : array[1..4] of word=(300,300,300,300};
-unsigned short  tx_BPF_timer[5] = {0};		//			 : array[1..4] of word=(0,0,0,0};
-UCHAR tx_pol[5] = {0};		//						 : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_last_pol[5] = {0};		//			  : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_last_diddle[5] = {0};		//     : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_flag_cnt[5] = {0};		//			  : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_frame_status[5] = {0};		//    : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_byte_status[5] = {0};		//     : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_status[5] = {0};		//			     : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_bit_stuff_cnt[5] = {0};		//    : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_bit_cnt[5] = {0};		//			    : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_last_bit[5] = {0};		//			   : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_bit_stream[5] = {0};		//			 : array[1..4] of byte=(0,0,0,0};
-
-UCHAR tx_8PSK[5] = {0};		//						 : array[1..4] of byte=(0,0,0,0};
-UCHAR tx_QPSK[5] = {0};		//						 : array[1..4] of byte=(0,0,0,0};
-
-float tx_I_mod[5] = {1, 1, 1, 1, 1};		//						: array[1..4] of single=(1,1,1,1};
-float tx_Q_mod[5] = {1, 1, 1, 1, 1};		//						: array[1..4] of single=(1,1,1,1};
-float tx_QPSK_avg_I[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_QPSK_avg_Q[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_QPSK_df_I[5] = {0};		//			  : array[1..4] of single=(0,0,0,0};
-float tx_QPSK_df_Q [5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_QPSK_I[5] = {0};		//			     : array[1..4] of single=(0,0,0,0};
-float tx_QPSK_Q[5] = {0};		//			     : array[1..4] of single=(0,0,0,0};
-float tx_QPSK_old_I[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_QPSK_old_Q[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_avg_I[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_avg_Q[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_df_I[5] = {0};		//			  : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_df_Q[5] = {0};		//			  : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_I[5] = {0};		//			     : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_Q[5] = {0};		//			     : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_old_I[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-float tx_8PSK_old_Q[5] = {0};		//			 : array[1..4] of single=(0,0,0,0};
-
-float tx_osc1[5] = {0};		//						 : array[1..4] of single=(0,0,0,0};
-float tx_osc2[5] = {0};		//						 : array[1..4] of single=(0,0,0,0};
-float tx_osc3[5] = {0};		//						 : array[1..4] of single=(0,0,0,0};
-float tx_osc4[5] = {0};		//						 : array[1..4] of single=(0,0,0,0};
-short tx_inv1[5] = {1, 1, 1, 1, 1};		//						: array[1..4] of shortint=(1,1,1,1};
-short tx_inv2[5] = {1, 1, 1, 1, 1};		//						: array[1..4] of shortint=(1,1,1,1};
-short tx_inv3[5] = {1, 1, 1, 1, 1};		//						: array[1..4] of shortint=(1,1,1,1};
-short tx_inv4[5] = {1, 1, 1, 1, 1};		//						: array[1..4] of shortint=(1,1,1,1};
-short tx_old_inv1[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of shortint=(1,1,1,1};
-short tx_old_inv2[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of shortint=(1,1,1,1};
-short tx_old_inv3[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of shortint=(1,1,1,1};
-short tx_old_inv4[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of shortint=(1,1,1,1};
-float tx_bit1_mod[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of single=(1,1,1,1};
-float tx_bit2_mod[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of single=(1,1,1,1};
-float tx_bit3_mod[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of single=(1,1,1,1};
-float tx_bit4_mod[5] = {1, 1, 1, 1, 1};		//			  : array[1..4] of single=(1,1,1,1};
-UINT tx_viterbi[5] = {0};		//			     : array[1..4] of word=(0,0,0,0};
-UCHAR tx_intv_tbl[5][4];		//			  : array[1..4,0..3] of byte;
-
-short tx_inv[5] = {1, 1, 1, 1, 1};		//						    : array[1..4] of shortint=(1,1,1,1};
-BOOL tx_change_phase[5] = {0};		//    : array[1..4] of boolean=(FALSE,FALSE,FALSE,FALSE};
-BOOL tx_bs_bit[5] = {0};		//			    : array[1..4] of boolean=(FALSE,FALSE,FALSE,FALSE};
-
-string * tx_data[5] = {0};		//						: array[1..4] of string=('','','',''};
-int tx_data_len[5] = {0};
-
-int tx_fx25_size[4] = { 0, 0, 0, 0 };
-int tx_fx25_size_cnt[4] = { 0, 0, 0, 0 };
-int tx_fx25_mode[4] = { 0, 0, 0, 0 };
-
-
-//  uses sm_main,ax25,ax25_agw,ax25_demod,rsunit;
-
-UCHAR tx_nrzi(UCHAR snd_ch, UCHAR bit)
-{
-//	Debugprintf("Before NRZI %d", bit);
-
-	if (bit == TX_BIT0)
-	{
-		// Zero so switch bit
-
-		tx_last_bit[snd_ch] ^= 1;
-	}
-	return tx_last_bit[snd_ch];	
-}
-
-BOOL tx_bit_stuffing(UCHAR snd_ch, UCHAR bit)
-{					 
- // result = FALSE;
- // if bit=TX_BIT1 then inc(tx_bit_stuff_cnt[snd_ch]};
- // if bit=TX_BIT0 then tx_bit_stuff_cnt[snd_ch] = 0;
- // if tx_bit_stuff_cnt[snd_ch]=5 then begin tx_bit_stuff_cnt[snd_ch] = 0; result = TRUE; end;
-//end;
-
-	if (bit == TX_BIT1)
-		tx_bit_stuff_cnt[snd_ch]++;
-
-	if (bit == TX_BIT0)
-		tx_bit_stuff_cnt[snd_ch] = 0;
-
-	if (tx_bit_stuff_cnt[snd_ch] == 5)
-	{
-		tx_bit_stuff_cnt[snd_ch] = 0;
-		return TRUE;
-	}
-
-	return FALSE;
-}
-
-
-
-
-void interleave(char *s, int len)
-{
-//	var
- // data: string;
- // i,k,len: word;
- // nr_blocks: word;
-//begin{
-//  data = '';
- // len = length(s};
- // if len>0 then nr_blocks = ((len-1} div 16}+1 else nr_blocks = 1;
- // for i = 1 to 16 do
- //   for k = 0 to nr_blocks-1 do
-  //   if (i+k*16}<=len then data = data+s[i+k*16];
- // result = data;
-//end;
-
-	char data[1024];
-
-	UINT i,k;
-	UINT nr_blocks;
-	int n = 0;
-
-	if (len > 0)
-		nr_blocks = ((len - 1) / 16) + 1;
-	else
-		nr_blocks = 1;
-
-	for (i = 0; i < 16; i++)
-	{
-		for (k = 0; k < nr_blocks; k++)
-		{
-			if ((i + k * 16) <= len)
-				data[n++] = s[i + k * 16];
-		}
-	}
-
-	memcpy(s, data, len);
-}
-
-//procedure get_new_frame(snd_ch: byte; var frame_stream: TStringList};
-//var
-//  header,line,temp: string;
-//  len,i,size: word;
- // crc: word;
-//begin
-
-void get_new_frame(UCHAR snd_ch, TStringList * frame_stream)
-{
-	UCHAR header[256];
-	UCHAR line[1024];
-
-	int LineLen;
-
-	string ** Items;
-
-	string * myTemp;
-
-	UCHAR temp[1024];
-
-	UINT len, i, size;
-	UINT crc;
-
-	tx_bs_bit[snd_ch] = FALSE;
-	tx_bit_cnt[snd_ch] = 0;
-	tx_flag_cnt[snd_ch] = 0;
-	tx_bit_stuff_cnt[snd_ch] = 0;
-	tx_bit_stream[snd_ch] = FRAME_FLAG;
-	tx_frame_status[snd_ch] = FRAME_NEW_FRAME;
-	tx_byte_status[snd_ch] = BYTE_EMPTY;
-
-	if (frame_stream->Count == 0)
-	{
-		tx_frame_status[snd_ch] = FRAME_NO_FRAME;
-		return;
-	}
-
-	// We now pass control byte and ack bytes on front and pointer to socket on end if ackmode
-
-	myTemp = Strings(frame_stream, 0);			// get message
-
-	if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-	{
-		// Save copy then copy data up 3 bytes
-
-		Add(&KISS_acked[snd_ch], duplicateString(myTemp));
-
-		mydelete(myTemp, 0, 3);
-		myTemp->Length -= sizeof(void *);
-	}
-	else
-	{
-		// Just remove control 
-
-		mydelete(myTemp, 0, 1);
-	}
-
-	tx_data[snd_ch] = duplicateString(myTemp);		// so can free original below
-
-	Delete(frame_stream, 0);			// This will invalidate temp
-
-	AGW_AX25_frame_analiz(snd_ch, FALSE, tx_data[snd_ch]);
-
-	put_frame(snd_ch, tx_data[snd_ch], "", TRUE, FALSE);
-
-	if (tx_data[snd_ch]->Length == 0 || modem_mode[snd_ch] != MODE_MPSK)
-		return;
-
-	// Reformat MPSK Data
-
-	//Take data 8 bytes at a time and add 8 bytes of RS data
-
-	LineLen = 0;
-
-	while (tx_data[snd_ch]->Length > 0)
-	{
-		size = tx_data[snd_ch]->Length;
-
-		if (size > 8)
-			size = 8;
-
-		memcpy(temp, tx_data[snd_ch]->Data, size);
-
-		// Delete the chars from tx_data
-
-		mydelete(tx_data[snd_ch], 0, 8);
-
-		memset(xData, 0, sizeof(xData));
-		memset(xEncoded, 0, sizeof(xEncoded));
-
-		memcpy(xData, temp, size);
-
-		InitBuffers();
-		EncodeRS(xData, xEncoded);			// This puts the 8 RS bytes in xEncoded
-
-		memcpy(&line[LineLen], xData, size);
-		memcpy(&line[LineLen + size], xEncoded, MaxErrors * 2);
-
-		LineLen += size + (MaxErrors * 2);
-	}
-
-
-
-
-	len = LineLen;
-
-	interleave(line, LineLen);
-	scrambler(line, LineLen);
-
-	header[0] = 0x7e;
-	header[1] = 0x7e;
-	header[2] = len >> 8;
-	header[3] = len;
-
-	crc = get_fcs(header, 4);
-
-	header[4] = crc >> 8;
-	header[5] = crc;
-
-	memset(xData, 0, sizeof(xData));
-	memset(xEncoded, 0, sizeof(xEncoded));
-	memmove(xData, header, 6);
-
-
-	//		RSEncode(xData, xEncoded, 6 + (MaxErrors * 2), MaxErrors * 2);
-
-	InitBuffers();
-	EncodeRS(xData, xEncoded);
-
-	fx25_encode_rs(xData, xEncoded, 0, 8);
-
-
-	// We should now have RS Encoded Header in xEncoded;
-
-	// I think we send encoded header then line
-
-	tx_data[snd_ch]->Length = 0;
-
-	stringAdd(tx_data[snd_ch], xData, 6);
-	stringAdd(tx_data[snd_ch], xEncoded, MaxErrors * 2);
-	stringAdd(tx_data[snd_ch], line, LineLen);
-
-	// For testing, descramble and de-interleve
-
-	scrambler(line, LineLen); // should look like interleaved
-	{
-		Byte unscrambled[1024];
-		int count, len;
-		int origlen;
-
-		len = LineLen;
-		count = (len + 15) / 16;
-
-		int j1, j2, j3, i, j;
-
-		j3 = 0;
-
-		for (j1 = 0; j1 < 16; j1++)
-		{
-			// Each char in block
-
-			for (j2 = 0; j2 < count; j2++)
-			{
-				// Blocks
-
-				unscrambled[j2 * 16 + j1] = line[j3];
-				j3++;
-			}
-		}
-
-		// Now remove RS (will check later)
-
-		i = 0;
-		j = 0;
-
-		while (j < len)
-		{
-			Byte line1[256];
-			int nErr, eras_pos = 0;
-			Byte rs_block[256];
-
-			memcpy(line1, &unscrambled[j], 16);
-
-			memset(xEncoded, 0, sizeof(xEncoded));
-			memset(xDecoded, 0, sizeof(xDecoded));
-
-			memcpy(xEncoded, &unscrambled[j], 16);
-
-//			nErr = DecodeRS(xEncoded, xDecoded);
-
-			memset(rs_block, 0, 255);
-			memcpy(rs_block, &unscrambled[j], 8);
-			memcpy(&rs_block[255 - 8], &unscrambled[j+8], 8);
-
-			nErr = fx25_decode_rs(rs_block, &eras_pos, 0, 0, 8);
-
-
-//			line1 = '';
-//			for j1 = MaxErrors * 2 to size - 1 do line1 = line1 + chr(xDecoded[j1]);
-
-
-			memcpy(&unscrambled[i], &unscrambled[j], 8);
-			i += 8;
-			j += 16;
-		}
-
-		j3 = j3;
-
-	}
-
-}
-  
-
-
-int get_new_bit(Byte snd_ch, Byte bit)
-{
-	unsigned short len;
-	string * s;
-
-	if (tx_frame_status[snd_ch] == FRAME_FULL)
-	{
-		if (tx_byte_status[snd_ch] == BYTE_EMPTY)
-		{
-			len = tx_data[snd_ch]->Length;
-
-			if (len > 0)
-			{
-				s = tx_data[snd_ch];
-				tx_bit_stream[snd_ch] = (s->Data[0]);
-				tx_frame_status[snd_ch] = FRAME_FULL;
-				tx_byte_status[snd_ch] = BYTE_FULL;
-				tx_bit_cnt[snd_ch] = 0;
-				mydelete(tx_data[snd_ch], 0, 1);
-			}
-
-			else tx_frame_status[snd_ch] = FRAME_EMPTY;
-		}
-
-		if (tx_byte_status[snd_ch] == BYTE_FULL)
-			bit = tx_bit_stream[snd_ch] & TX_BIT1;
-
-		if (modem_mode[snd_ch] == MODE_MPSK)
-		{
-			tx_bit_cnt[snd_ch]++;
-			tx_bit_stream[snd_ch] = tx_bit_stream[snd_ch] >> 1;
-			if (tx_bit_cnt[snd_ch] >= 8)
-				tx_byte_status[snd_ch] = BYTE_EMPTY;
-
-		}
-		else
-		{
-			if (tx_bs_bit[snd_ch])
-				bit = TX_BIT0;
-
-			tx_bs_bit[snd_ch] = tx_bit_stuffing(snd_ch, bit);
-
-			if (!tx_bs_bit[snd_ch])
-			{
-				tx_bit_cnt[snd_ch]++;
-				tx_bit_stream[snd_ch] >>= 1;
-				if (tx_bit_cnt[snd_ch] >= 8 && !tx_bs_bit[snd_ch])
-					tx_byte_status[snd_ch] = BYTE_EMPTY;
-			}
-		}
-	}
-
-	if (tx_frame_status[snd_ch] == FRAME_EMPTY)
-		get_new_frame(snd_ch, &all_frame_buf[snd_ch]);
-
-	if ((tx_frame_status[snd_ch] == FRAME_NEW_FRAME) || (tx_frame_status[snd_ch] == FRAME_NO_FRAME))
-	{
-		bit = tx_bit_stream[snd_ch] & TX_BIT1;
-		tx_flag_cnt[snd_ch]++;
-		tx_bit_stream[snd_ch] >>= 1;
-
-		if (tx_flag_cnt[snd_ch] == 8)
-		{
-			switch (tx_frame_status[snd_ch])
-			{
-			case FRAME_NEW_FRAME:
-
-				tx_frame_status[snd_ch] = FRAME_FULL;
-				break;
-
-			case FRAME_NO_FRAME:
-
-				tx_tail_cnt[snd_ch] = 0;
-				tx_frame_status[snd_ch] = FRAME_EMPTY;
-				tx_status[snd_ch] = TX_TAIL;
-
-				break;
-			}
-		}
-	}
-	return bit;
-}
-
-////// FX.25 //////
-
-
-void bit_to_fx25(Byte * tx_byte,  Byte * bit_cnt, Byte bit, string * data, int * data_cnt)
-{
-	*tx_byte = (*tx_byte >> 1) | (bit << 7);
-	(*bit_cnt)++;
-
-	if (*bit_cnt == 8)
-	{
-		stringAdd(data, tx_byte, 1);
-		*bit_cnt = 0;
-	}
-	(*data_cnt)++;
-}
-
-string * fill_fx25_data(int snd_ch, string * data)
-{
-#define nr_tags 5
-
-	string * result;
-
-	Byte rs_roots[nr_tags + 1] = { 16, 32, 64, 32, 16, 16 };
-	word rs_payload[nr_tags + 1] = { 1912, 1784, 1528, 1024, 512, 256 }; // 239, 233, 191, 128, 64, 32
-
-	unsigned long long rs_tag[nr_tags + 1] =
-	{
-		0xB74DB7DF8A532F3E,			// 255 / 16 (239)
-		0x6E260B1AC5835FAE,			// 255 / 32 (223)
-		0x3ADB0C13DEAE2836,			// 255 / 64 (191)
-		0xFF94DC634F1CFF4E,			// 160 / 32 (128)
-		0xC7DC0508F3D9B09E,			// 80 / 16	(64)	
-		0x8F056EB4369660EE 		// 48 / 16	(32)
-	};
-
-//	0x26FF60A600CC8FDE) 144; = 16;
-//	0x1EB7B9CDBC09C00E) 96; 32;
-//  0xDBF869BD2DBB1776) 64;= 32;
-//	0xAB69DB6A543188D6) 192; = 64;
-//	0x4A4ABEC4A724B796) 128; = 64;
-
-	string * ax25_data = newString();
-
-	int i, ax25_size;
-	Byte a, bit, bit_cnt, bit_cnt1, bs, tx_byte;
-	Byte rs_id;
-	Byte rs_block[256], parity[256];
-
-	ax25_size = 0;
-	bs = 0;
-	tx_byte = 0;
-	bit_cnt = 0;
-
-	// Load start flag
-	a = FRAME_FLAG;
-
-	for (i = 0; i < 8; i++)
-	{
-		bit = a & 1;
-		a = a >> 1;
-		bit_to_fx25(&tx_byte, &bit_cnt, bit, ax25_data, &ax25_size);
-	}
-
-	// Load body
-	for (i = 0; i < data->Length; i++)
-	{
-		bit_cnt1 = 0;
-		a = data->Data[i];
-		do
-		{
-			if (bs == 5)
-			{
-				bit = TX_BIT0;
-				bs = 0;
-			}
-			else
-			{
-				bit = a & 1;
-				a = a >> 1;
-				bit_cnt1++;
-
-				if (bit == TX_BIT1)
-					bs++;
-				else
-					bs = 0;
-			}
-
-			bit_to_fx25(&tx_byte, &bit_cnt, bit, ax25_data, &ax25_size);
-
-		} while (bit_cnt1 != 8 || bs == 5);
-	}
-
-	// Load close flag
-
-	a = FRAME_FLAG;
-
-	for (i = 0; i < 8; i++)
-	{
-		bit = a & 1;
-		a = a >> 1;
-		bit_to_fx25(&tx_byte, &bit_cnt, bit, ax25_data, &ax25_size);
-	}
-
-	a = FRAME_FLAG;
-
-	// if too short or too long 
-
-	if (ax25_size < 168 || ax25_size > 1912)	// < 21 or > 239
-	{
-		// Send as normal ax25 packet
-
-		if (bit_cnt > 0)
-		{
-			do
-			{
-				tx_byte = tx_byte >> 1;
-				bit_cnt++;
-				if (bit_cnt == 8)
-					stringAdd(ax25_data, &tx_byte, 1);
-			} while (bit_cnt < 8);
-		}
-		tx_fx25_size[snd_ch] = ax25_size;
-		return ax25_data;
-	}
-
-	// Send as FX25 Message
-
-	// find RS block size
-
-	rs_id = 0;
-
-	for (i = 0; i <= nr_tags; i++)
-		if (ax25_size <= rs_payload[i])
-			rs_id = i;
-
-	// Padding to block size
-
-	while (ax25_size != rs_payload[rs_id])
-	{
-		bit = a & 1;
-		a = (a >> 1) | (bit << 7);
-		bit_to_fx25(&tx_byte, &bit_cnt, bit, ax25_data, &ax25_size);
-	}
-
-	memset(rs_block, 0, 255);
-	move(&ax25_data->Data[0], &rs_block[0], ax25_data->Length);
-
-	fx25_encode_rs(rs_block, parity, 0, rs_roots[rs_id]);
-
-	result = newString();
-
-	stringAdd(result, (Byte *)&rs_tag[rs_id], 8);
-	stringAdd(result, ax25_data->Data, ax25_data->Length);
-	stringAdd(result, parity, rs_roots[rs_id]);
-
-	tx_fx25_size[snd_ch] = result->Length << 3;
-
-	freeString(ax25_data);
-	return result;
-}
-
-void fx25_get_new_frame(int snd_ch, TStringList * frame_stream)
-{
-	string * myTemp;
-
-	tx_bs_bit[snd_ch] = 0;
-	tx_bit_cnt[snd_ch] = 0;
-	tx_flag_cnt[snd_ch] = 0;
-	tx_bit_stuff_cnt[snd_ch] = 0;
-	tx_fx25_size_cnt[snd_ch] = 0;
-	tx_fx25_size[snd_ch] = 1;
-	tx_frame_status[snd_ch] = FRAME_NEW_FRAME;
-	tx_byte_status[snd_ch] = BYTE_EMPTY;
-	if (frame_stream->Count == 0)
-		tx_frame_status[snd_ch] = FRAME_NO_FRAME;
-	else
-	{
-		// We now pass control byte and ack bytes on front and pointer to socket on end if ackmode
-
-		myTemp = Strings(frame_stream, 0);			// get message
-
-		if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-		{
-			// Save copy then copy data up 3 bytes
-
-			Add(&KISS_acked[snd_ch], duplicateString(myTemp));
-
-			mydelete(myTemp, 0, 3);
-			myTemp->Length -= sizeof(void *);
-		}
-		else
-		{
-			// Just remove control 
-
-			mydelete(myTemp, 0, 1);
-		}
-
-		AGW_AX25_frame_analiz(snd_ch, FALSE, myTemp);
-		put_frame(snd_ch, myTemp, "", TRUE, FALSE);
-
-		tx_data[snd_ch] = fill_fx25_data(snd_ch, myTemp);
-
-		Delete(frame_stream, 0);			// This will invalidate temp
-	}
-}
-
-int fx25_get_new_bit(int snd_ch, Byte bit)
-{
-	string *s;
-
-	if (tx_frame_status[snd_ch] == FRAME_EMPTY)
-	{
-		fx25_get_new_frame(snd_ch, &all_frame_buf[snd_ch]);
-		if (tx_frame_status[snd_ch] == FRAME_NEW_FRAME)
-			tx_frame_status[snd_ch] = FRAME_FULL;
-	}
-
-	if (tx_frame_status[snd_ch] == FRAME_FULL)
-	{
-		if (tx_byte_status[snd_ch] == BYTE_EMPTY)
-		{
-			if (tx_data[snd_ch]->Length)
-			{
-				s = tx_data[snd_ch];
-
-				tx_bit_stream[snd_ch] = s->Data[0];
-				tx_frame_status[snd_ch] = FRAME_FULL;
-				tx_byte_status[snd_ch] = BYTE_FULL;
-				tx_bit_cnt[snd_ch] = 0;
-				mydelete(tx_data[snd_ch], 0, 1);
-			}
-			else
-				tx_frame_status[snd_ch] = FRAME_EMPTY;
-		}
-		if (tx_byte_status[snd_ch] == BYTE_FULL)
-		{
-			bit = tx_bit_stream[snd_ch] & TX_BIT1;
-			tx_bit_stream[snd_ch] = tx_bit_stream[snd_ch] >> 1;
-			tx_bit_cnt[snd_ch]++;
-			tx_fx25_size_cnt[snd_ch]++;
-			if (tx_bit_cnt[snd_ch] >= 8)
-				tx_byte_status[snd_ch] = BYTE_EMPTY;
-			if (tx_fx25_size_cnt[snd_ch] == tx_fx25_size[snd_ch])
-				tx_frame_status[snd_ch] = FRAME_EMPTY;
-		}
-	}
-
-	if (tx_frame_status[snd_ch] == FRAME_EMPTY)
-	{
-		fx25_get_new_frame(snd_ch, &all_frame_buf[snd_ch]);
-
-		switch (tx_frame_status[snd_ch])
-		{
-		case FRAME_NEW_FRAME:
-			tx_frame_status[snd_ch] = FRAME_FULL;
-			break;
-
-		case FRAME_NO_FRAME:
-			tx_tail_cnt[snd_ch] = 0;
-			tx_frame_status[snd_ch] = FRAME_EMPTY;
-			tx_status[snd_ch] = TX_TAIL;
-			break;
-		}
-	}
-	return bit;
-}
-
-
-//////////////////
-
-
-int get_new_bit_tail(UCHAR snd_ch, UCHAR bit)
-{
-	long _txtail = 0;
-	UCHAR _diddles;
-
-	if (modem_mode[snd_ch] == MODE_FSK)
-		_diddles = diddles;
-	else
-		_diddles = 0;
-
-	if (modem_mode[snd_ch] == MODE_FSK)
-		_txtail = txtail[snd_ch];
-
-	else if (modem_mode[snd_ch] == MODE_BPSK)
-		_txtail = txtail[snd_ch];
-
-	else if (modem_mode[snd_ch] == MODE_8PSK)
-		_txtail = txtail[snd_ch] * 3;
-
-	else if (modem_mode[snd_ch] == MODE_QPSK || modem_mode[snd_ch] == MODE_PI4QPSK)
-	  _txtail = txtail[snd_ch] << 1;
-  
-	else if (modem_mode[snd_ch] == MODE_MPSK)
-		_txtail = txtail[snd_ch] << 2;
-
-	_txtail = (_txtail * tx_baudrate[snd_ch]) / 1000;
-
-	if (qpsk_set[snd_ch].mode == QPSK_V26 || modem_mode[snd_ch] == MODE_8PSK)
-		_diddles = 2;
-
-	switch (_diddles)
-	{
-	case 0:
-    
-		if (tx_tail_cnt[snd_ch] < _txtail)
-		{
-			bit = TX_BIT0;
-			tx_tail_cnt[snd_ch]++;
-		}
-		else
-		{
-			tx_status[snd_ch] = TX_WAIT_BPF;
-		}
-
-		break;
-
-	case 1:
-
-		if (tx_tail_cnt[snd_ch] < _txtail)
-		{
-			if (tx_last_diddle[snd_ch] == TX_BIT0)
-				bit = TX_BIT1;
-			else
-				bit = TX_BIT0;
-
-			tx_tail_cnt[snd_ch]++;
-			tx_last_diddle[snd_ch] = bit;
-		}
-		else
-		{
-			Debugprintf("End TXTAIL %d", SampleNo);
-			tx_status[snd_ch] = TX_WAIT_BPF;
-		}
-		
-		break;
-	
-	case 2:
-    
-		if (tx_tail_cnt[snd_ch] < _txtail)
-		{
-			bit = FRAME_FLAG >> (tx_tail_cnt[snd_ch] % 8) & 1;
-			tx_tail_cnt[snd_ch]++;
-		}
-		else
-		{
-			Debugprintf("End TXTAIL %d", SampleNo);
-			tx_status[snd_ch] = TX_WAIT_BPF;
-		}
-		break;
-	}
-	return bit;
-}
-
-int get_new_bit_delay(UCHAR snd_ch, UCHAR bit)
-{
-	ULONG _txdelay = 0;
-	UCHAR _diddles;
-
-	_diddles = 0;
-
-	switch (modem_mode[snd_ch])
-	{
-	case MODE_FSK:
-	
-		_diddles = diddles;
-		break;
-
-	case MODE_PI4QPSK:
-	case MODE_8PSK:
-
-		_diddles = 2;
-		break;
-
-    case MODE_QPSK:
-		
-		if (qpsk_set[snd_ch].mode == QPSK_V26)
-			_diddles = 2;
-		break;
-	}
-
-	if (modem_mode[snd_ch] == MODE_FSK)
-		_txdelay = txdelay[snd_ch];
-
-	else if (modem_mode[snd_ch] == MODE_BPSK)
-		_txdelay = txdelay[snd_ch];
-
-	else if (modem_mode[snd_ch] == MODE_8PSK)
-		_txdelay = txdelay[snd_ch] * 3;
-
-	else if (modem_mode[snd_ch] == MODE_QPSK || modem_mode[snd_ch] == MODE_PI4QPSK)
-		_txdelay = txdelay[snd_ch] << 1;
-
-	else if (modem_mode[snd_ch] == MODE_MPSK)
-	{
-		if (txdelay[snd_ch] < 400)
-			_txdelay = 400 << 2;		 //AFC delay
-		else
-			_txdelay = txdelay[snd_ch] << 2;
-	}
-	
-	_txdelay = (_txdelay * tx_baudrate[snd_ch]) / 1000;
-
-	switch (_diddles)
-	{
-	case 0:
-   
-		if (tx_delay_cnt[snd_ch] < _txdelay)
-		{
-			bit = TX_BIT0;
-			tx_delay_cnt[snd_ch]++;
-		}
-		else
-		{
-			tx_status[snd_ch] = TX_FRAME;
-		}
-
-		break;	
-	
-	case 1:
-    
-		if (tx_delay_cnt[snd_ch] < _txdelay)
-		{
-			if (tx_last_diddle[snd_ch] == TX_BIT0)
-				bit = TX_BIT1;
-			else
-				bit = TX_BIT0;
-		
-			tx_delay_cnt[snd_ch]++;
-			tx_last_diddle[snd_ch] = bit;
-		}
-		else
-		{
-			tx_status[snd_ch] = TX_FRAME;
-			Debugprintf("End TXD %d", SampleNo);
-		}
-		break;
-
-	case 2:
-
-		// Send Flags
-
-		if (tx_delay_cnt[snd_ch] < _txdelay)
-		{
-			bit = FRAME_FLAG >> ((8 - (_txdelay % 8) + tx_delay_cnt[snd_ch]) % 8) & 1;
-			tx_delay_cnt[snd_ch]++;
-		}
-		else
-		{
-			tx_status[snd_ch] = TX_FRAME;
-			Debugprintf("End TXD %d", SampleNo);
-		}
-		break;
-	}
-	return bit;
-}
-
-// is this waiting for the filter to fill?
-// No, flushing BPF
-
-void get_wait_bpf(UCHAR snd_ch)
-{
-	tx_BPF_timer[snd_ch]++;
-
-	if (tx_BPF_timer[snd_ch] == tx_BPF_tap[snd_ch] )
-	{
-		tx_status[snd_ch] = TX_NO_DATA;
-		tx_BPF_timer[snd_ch] = 0;
-	}
-}
-
-
-//procedure modulator(snd_ch: byte; var buf: array of single; buf_size: word};
-//{
-/*
-function filter(x,k: single}: single;
-begin
-  result = k*cos(x};
-  if result>1 then result = 1;
-  if result<-1 then result = -1;
-end;
-}
-*/
-
-single filter(single x)
-{
-	if (x <= PI25)
-		return 1.0f;
-
-	if (x >= PI75)
-		return  -1.0f;
-
-     return cosf(2.0f * x -PI5);
-}
-
-
-// make_samples return one sample of the waveform
-
-// But seems to be called only once per bit ??
-
-// No, but needs to preserve bit between calls 
-
-float make_samples(unsigned char  snd_ch, unsigned char * bitptr)
-{
-	float pi2, x1, x;
-	Byte i,qbit,tribit,dibit;
-	float z1,z2,z3,z4;
-	unsigned short b, msb, lsb;
-	unsigned char bit = *bitptr;
-
-	float amp = 0;
-
-	pi2 = 2 * pi / TX_Samplerate;
-	x1 = pi * tx_baudrate[snd_ch] / TX_Samplerate;
-
-	if (modem_mode[snd_ch] == MODE_FSK)
-	{
-		if (bit == TX_BIT0)
-			x = pi2*(tx_freq[snd_ch] + 0.5f * tx_shift[snd_ch]);
-		else
-			x = pi2*(tx_freq[snd_ch] - 0.5f * tx_shift[snd_ch]);
-
-	   amp = 1.0f;
-
-	    if (tx_baudrate[snd_ch] > 600)
-		{
-			if (tx_hitoneraisedb[snd_ch] < 0 && bit == TX_BIT0)
-				amp = tx_hitoneraise[snd_ch];
-
-			if (tx_hitoneraisedb[snd_ch] > 0 && bit == TX_BIT1)
-				amp = tx_hitoneraise[snd_ch];
-		}
-
-		tx_osc[snd_ch] = tx_osc[snd_ch] + x;
-
-		if (tx_osc[snd_ch] > 2*pi)
-			tx_osc[snd_ch] = tx_osc[snd_ch] - 2*pi;
-	}
-
-	else if (modem_mode[snd_ch] == MODE_BPSK)
-	{
-		if (tx_change_phase[snd_ch])
-			tx_bit_mod[snd_ch] = tx_inv[snd_ch] * cos(tx_bit_osc[snd_ch]);
-
-		x = pi2 * (tx_freq[snd_ch]);
-
-		tx_osc[snd_ch] = tx_osc[snd_ch] + x;
-
-		if (tx_osc[snd_ch] > 2 * pi)
-			tx_osc[snd_ch] = tx_osc[snd_ch] - 2 * pi;
-	}
-
-	else if (modem_mode[snd_ch] == MODE_QPSK)
-	{
-		if (tx_QPSK_old_I[snd_ch] != tx_QPSK_I[snd_ch])
-
-			tx_I_mod[snd_ch] = tx_QPSK_avg_I[snd_ch] + tx_QPSK_df_I[snd_ch] * filter(tx_bit_osc[snd_ch]);
-		else
-			tx_I_mod[snd_ch] = tx_QPSK_I[snd_ch];
-
-		if (tx_QPSK_old_Q[snd_ch] != tx_QPSK_Q[snd_ch])
-			tx_Q_mod[snd_ch] = tx_QPSK_avg_Q[snd_ch] + tx_QPSK_df_Q[snd_ch] * filter(tx_bit_osc[snd_ch]);
-		else
-			tx_Q_mod[snd_ch] = tx_QPSK_Q[snd_ch];
-
-		x = pi2 * (tx_freq[snd_ch]);
-		tx_osc[snd_ch] = tx_osc[snd_ch] + x;
-		if (tx_osc[snd_ch] > 2 * pi)
-			tx_osc[snd_ch] = tx_osc[snd_ch] - 2 * pi;
-	}
-  
-	else if (modem_mode[snd_ch] == MODE_8PSK || modem_mode[snd_ch] == MODE_PI4QPSK)
-	{
-		if (tx_8PSK_old_I[snd_ch] != tx_8PSK_I[snd_ch])
-			tx_I_mod[snd_ch] = tx_8PSK_avg_I[snd_ch] + tx_8PSK_df_I[snd_ch] * filter(tx_bit_osc[snd_ch]);
-		else
-			tx_I_mod[snd_ch] = tx_8PSK_I[snd_ch];
-
-		if (tx_8PSK_old_Q[snd_ch] != tx_8PSK_Q[snd_ch])
-			tx_Q_mod[snd_ch] = tx_8PSK_avg_Q[snd_ch] + tx_8PSK_df_Q[snd_ch] * filter(tx_bit_osc[snd_ch]);
-		else
-			tx_Q_mod[snd_ch] = tx_8PSK_Q[snd_ch];
-
-		x = pi2 * (tx_freq[snd_ch]);
-		tx_osc[snd_ch] = tx_osc[snd_ch] + x;
-
-		if (tx_osc[snd_ch] > 2 * pi)
-			tx_osc[snd_ch] = tx_osc[snd_ch] - 2 * pi;
-
-	}
-
-	else if (modem_mode[snd_ch] == MODE_MPSK)
-	{
-		z1 = pi2 * (tx_freq[snd_ch] + ch_offset[0]);
-		z2 = pi2 * (tx_freq[snd_ch] + ch_offset[1]);
-		z3 = pi2 * (tx_freq[snd_ch] + ch_offset[2]);
-		z4 = pi2 * (tx_freq[snd_ch] + ch_offset[3]);
-
-		tx_osc1[snd_ch] = tx_osc1[snd_ch] + z1;
-		tx_osc2[snd_ch] = tx_osc2[snd_ch] + z2;
-		tx_osc3[snd_ch] = tx_osc3[snd_ch] + z3;
-		tx_osc4[snd_ch] = tx_osc4[snd_ch] + z4;
-
-		if (tx_osc1[snd_ch] > 2 * pi)
-			tx_osc1[snd_ch] = tx_osc1[snd_ch] - 2 * pi;
-
-		if (tx_osc2[snd_ch] > 2 * pi)
-			tx_osc2[snd_ch] = tx_osc2[snd_ch] - 2 * pi;
-
-		if (tx_osc3[snd_ch] > 2 * pi)
-			tx_osc3[snd_ch] = tx_osc3[snd_ch] - 2 * pi;
-
-		if (tx_osc4[snd_ch] > 2 * pi)
-			tx_osc4[snd_ch] = tx_osc4[snd_ch] - 2 * pi;
-
-		if (tx_old_inv1[snd_ch] != tx_inv1[snd_ch])
-			tx_bit1_mod[snd_ch] = tx_inv1[snd_ch] * cos(tx_bit_osc[snd_ch]);
-		else
-			tx_bit1_mod[snd_ch] = -tx_inv1[snd_ch];
-
-		if (tx_old_inv2[snd_ch] != tx_inv2[snd_ch])
-			tx_bit2_mod[snd_ch] = tx_inv2[snd_ch] * cos(tx_bit_osc[snd_ch]);
-		else 
-			tx_bit2_mod[snd_ch] = -tx_inv2[snd_ch];
-
-		if (tx_old_inv3[snd_ch] != tx_inv3[snd_ch])
-			tx_bit3_mod[snd_ch] = tx_inv3[snd_ch] * cos(tx_bit_osc[snd_ch]);
-		else 
-			tx_bit3_mod[snd_ch] = -tx_inv3[snd_ch];
-
-		if (tx_old_inv4[snd_ch] != tx_inv4[snd_ch]) 
-			tx_bit4_mod[snd_ch] = tx_inv4[snd_ch] * cos(tx_bit_osc[snd_ch]);
-		else
-			tx_bit4_mod[snd_ch] = -tx_inv4[snd_ch];
-	}
-
-	tx_bit_osc[snd_ch] = tx_bit_osc[snd_ch] + x1;
-
-	if (tx_bit_osc[snd_ch] > pi)
-	{
-		// This seems to get the next bit,
-		// but why?? - end of samples for last bit
-
-		tx_bit_osc[snd_ch] = tx_bit_osc[snd_ch] - pi;
-
-		// FSK Mode
-		if (modem_mode[snd_ch] == MODE_FSK)
-		{
-			bit = 0;
-
-			if (tx_status[snd_ch] == TX_SILENCE)
-			{
-				tx_delay_cnt[snd_ch] = 0;
-				tx_status[snd_ch] = TX_DELAY;
-			}
-	
-			if (il2p_mode[snd_ch] >= IL2P_MODE_TXRX)
-			{
-				// il2p generates TXDELAY as part of the frame, so go straight to TX_FRAME
-			
-				if (tx_status[snd_ch] == TX_DELAY)
-					tx_status[snd_ch] = TX_FRAME;
-	
-				if (tx_status[snd_ch] == TX_TAIL)
-					bit = get_new_bit_tail(snd_ch, bit);
-
-				if (tx_status[snd_ch] == TX_FRAME)
-					bit = il2p_get_new_bit(snd_ch, bit);
-
-
-				// No nrzi for il2p
-
-				*bitptr = bit;
-			}
-			else
-			{
-				// ax25/fx25
-
-				if (tx_status[snd_ch] == TX_DELAY)
-					bit = get_new_bit_delay(snd_ch, bit);
-
-				if (tx_status[snd_ch] == TX_TAIL)
-					bit = get_new_bit_tail(snd_ch, bit);
-
-				if (tx_status[snd_ch] == TX_FRAME)
-				{
-					if (tx_fx25_mode[snd_ch])
-						bit = fx25_get_new_bit(snd_ch, bit);
-					else
-						bit = get_new_bit(snd_ch, bit);
-				}
-				
-				*bitptr = tx_nrzi(snd_ch, bit);
-
-			}
-		}
-
-		// BPSK Mode
-		if (modem_mode[snd_ch] == MODE_BPSK)
-		{
-			bit = 0;
-
-			if (tx_status[snd_ch] == TX_SILENCE)
-			{
-				tx_delay_cnt[snd_ch] = 0;
-				Debugprintf("Start TXD");
-				tx_status[snd_ch] = TX_DELAY;
-			}
-
-
-
-			// il2p generates TXDELAY as part of the frame, so go straight too TX_FRAME
-
-			if (tx_status[snd_ch] == TX_DELAY)
-				if (il2p_mode[snd_ch] >= IL2P_MODE_TXRX)
-					tx_status[snd_ch] = TX_FRAME;
-				else
-					bit = get_new_bit_delay(snd_ch, bit);
-
-			if (tx_status[snd_ch] == TX_TAIL)
-				bit = get_new_bit_tail(snd_ch, bit);
-
-			if (tx_status[snd_ch] == TX_FRAME)
-			{
-				if (il2p_mode[snd_ch] >= IL2P_MODE_TXRX)
-					bit = il2p_get_new_bit(snd_ch, bit);
-				else if (tx_fx25_mode[snd_ch])
-					bit = fx25_get_new_bit(snd_ch, bit);
-				else
-					bit = get_new_bit(snd_ch, bit);
-			}
-			// ??			*bitptr = tx_nrzi(snd_ch, bit);
-
-			if (bit == 0)
-			{
-				tx_inv[snd_ch] = -tx_inv[snd_ch];
-				tx_change_phase[snd_ch] = TRUE;
-			}
-			else
-				tx_change_phase[snd_ch] = FALSE;
-		}
-
-		// QPSK Mode
-
-		else if (modem_mode[snd_ch] == MODE_QPSK)
-		{
-			dibit = 0;
-			for (i = 0; i < 2; i++)
-			{
-				bit = 0;
-				if (tx_status[snd_ch] == TX_SILENCE)
-				{
-					tx_delay_cnt[snd_ch] = 0;
-					tx_status[snd_ch] = TX_DELAY;
-				}
-
-				if (il2p_mode[snd_ch] >= IL2P_MODE_TXRX)
-				{
-					if (tx_status[snd_ch] == TX_DELAY)
-						tx_status[snd_ch] = TX_FRAME;			// il2p generates TXDELAY as part of the frame, so go straight to TX_FRAME
-
-					if (tx_status[snd_ch] == TX_TAIL)
-						bit = get_new_bit_tail(snd_ch, bit);
-
-					if (tx_status[snd_ch] == TX_FRAME)
-						bit = il2p_get_new_bit(snd_ch, bit);
-
-					// No nrzi for il2p
-
-					dibit = (dibit << 1) | bit;
-				}
-				else
-				{
-					// ax25/fx25
-
-					if (tx_status[snd_ch] == TX_DELAY)
-						bit = get_new_bit_delay(snd_ch, bit);
-					if (tx_status[snd_ch] == TX_TAIL)
-						bit = get_new_bit_tail(snd_ch, bit);
-					if (tx_status[snd_ch] == TX_FRAME)
-						bit = get_new_bit(snd_ch, bit);
-					dibit = (dibit << 1) | tx_nrzi(snd_ch, bit);
-
-				}
-			}
-
-
-			dibit = qpsk_set[snd_ch].tx[dibit & 3];
-			tx_QPSK[snd_ch] = (tx_QPSK[snd_ch] + dibit) & 3;
-			tx_QPSK_old_I[snd_ch] = tx_QPSK_I[snd_ch];
-			tx_QPSK_old_Q[snd_ch] = tx_QPSK_Q[snd_ch];
-
-			switch (tx_QPSK[snd_ch])
-			{
-			case 0:
-
-				tx_QPSK_I[snd_ch] = COS45;
-				tx_QPSK_Q[snd_ch] = COS45;
-				break;
-
-			case 1:
-
-				tx_QPSK_I[snd_ch] = -COS45;
-				tx_QPSK_Q[snd_ch] = COS45;
-				break;
-
-			case 2:
-
-				tx_QPSK_I[snd_ch] = -COS45;
-				tx_QPSK_Q[snd_ch] = -COS45;
-				break;
-
-			case 3:
-
-				tx_QPSK_I[snd_ch] = COS45;
-				tx_QPSK_Q[snd_ch] = -COS45;
-				break;
-			}
-
-			tx_QPSK_avg_I[snd_ch] = 0.5f*(tx_QPSK_old_I[snd_ch] + tx_QPSK_I[snd_ch]);
-			tx_QPSK_df_I[snd_ch] = 0.5f*(tx_QPSK_old_I[snd_ch] - tx_QPSK_I[snd_ch]);
-			tx_QPSK_avg_Q[snd_ch] = 0.5f*(tx_QPSK_old_Q[snd_ch] + tx_QPSK_Q[snd_ch]);
-			tx_QPSK_df_Q[snd_ch] = 0.5f*(tx_QPSK_old_Q[snd_ch] - tx_QPSK_Q[snd_ch]);
-		}
-
-		// PI/4 QPSK Mode
-
-		if (modem_mode[snd_ch] == MODE_PI4QPSK)
-		{
-			dibit = 0;
-
-			for (i = 0; i < 2; i++)
-			{
-				bit = 0;
-				if (tx_status[snd_ch] == TX_SILENCE)
-				{
-					tx_delay_cnt[snd_ch] = 0;
-					Debugprintf("Start TXD");
-					tx_status[snd_ch] = TX_DELAY;
-				}
-
-				if (il2p_mode[snd_ch] >= IL2P_MODE_TXRX)
-				{
-					if (tx_status[snd_ch] == TX_DELAY)
-						tx_status[snd_ch] = TX_FRAME;			// il2p generates TXDELAY as part of the frame, so go straight to TX_FRAME
-
-					if (tx_status[snd_ch] == TX_TAIL)
-						bit = get_new_bit_tail(snd_ch, bit);
-
-					if (tx_status[snd_ch] == TX_FRAME)
-						bit = il2p_get_new_bit(snd_ch, bit);
-
-					// No nrzi for il2p
-
-					dibit = (dibit << 1) | bit;
-				}
-				else
-				{
-					// ax25/fx25
-
-					if (tx_status[snd_ch] == TX_DELAY)
-						bit = get_new_bit_delay(snd_ch, bit);
-
-					if (tx_status[snd_ch] == TX_TAIL)
-						bit = get_new_bit_tail(snd_ch, bit);
-
-					if (tx_status[snd_ch] == TX_FRAME)
-						bit = get_new_bit(snd_ch, bit);
-
-					*bitptr = tx_nrzi(snd_ch, bit);
-			
-					dibit = (dibit << 1) | *bitptr;
-				}
-			}
-
-			// This returns 3,1,5 or 7 so we use the odd enties in the 8PSK table
-
-			dibit = gray_PI4QPSK[dibit & 3];
-
-			tx_8PSK[snd_ch] = (tx_8PSK[snd_ch] + dibit) & 7;
-			tx_8PSK_old_I[snd_ch] = tx_8PSK_I[snd_ch];
-			tx_8PSK_old_Q[snd_ch] = tx_8PSK_Q[snd_ch];
-
-			switch (tx_8PSK[snd_ch])
-			{
-			case 0:
-				tx_8PSK_I[snd_ch] = 0;
-				tx_8PSK_Q[snd_ch] = 1;
-				break;
-
-			case 1:
-				tx_8PSK_I[snd_ch] = COS45;
-				tx_8PSK_Q[snd_ch] = COS45;
-				break;
-
-			case 2:
-				tx_8PSK_I[snd_ch] = 1;
-				tx_8PSK_Q[snd_ch] = 0;
-				break;
-
-			case 3:
-				tx_8PSK_I[snd_ch] = COS45;
-				tx_8PSK_Q[snd_ch] = -COS45;
-				break;
-
-			case 4:
-				tx_8PSK_I[snd_ch] = 0;
-				tx_8PSK_Q[snd_ch] = -1;
-				break;
-
-			case 5:
-				tx_8PSK_I[snd_ch] = -COS45;
-				tx_8PSK_Q[snd_ch] = -COS45;
-				break;
-
-			case 6:
-				tx_8PSK_I[snd_ch] = -1;
-				tx_8PSK_Q[snd_ch] = 0;
-				break;
-
-			case 7:
-				tx_8PSK_I[snd_ch] = -COS45;
-				tx_8PSK_Q[snd_ch] = COS45;
-				break;
-
-			}
-
-			tx_8PSK_avg_I[snd_ch] = 0.5*(tx_8PSK_old_I[snd_ch] + tx_8PSK_I[snd_ch]);
-			tx_8PSK_df_I[snd_ch] = 0.5*(tx_8PSK_old_I[snd_ch] - tx_8PSK_I[snd_ch]);
-			tx_8PSK_avg_Q[snd_ch] = 0.5*(tx_8PSK_old_Q[snd_ch] + tx_8PSK_Q[snd_ch]);
-			tx_8PSK_df_Q[snd_ch] = 0.5*(tx_8PSK_old_Q[snd_ch] - tx_8PSK_Q[snd_ch]);
-
-		}
-		
-		// 8PSK Mode
-
-		if (modem_mode[snd_ch] == MODE_8PSK)
-		{
-			tribit = 0;
-			for (i = 0; i < 3; i++)
-			{
-				bit = 0;
-
-				if (tx_status[snd_ch] == TX_SILENCE)
-				{
-					tx_delay_cnt[snd_ch] = 0;
-					tx_status[snd_ch] = TX_DELAY;
-				}
-
-				if (il2p_mode[snd_ch] >= IL2P_MODE_TXRX)
-				{
-					if (tx_status[snd_ch] == TX_DELAY)
-						tx_status[snd_ch] = TX_FRAME;			// il2p generates TXDELAY as part of the frame, so go straight to TX_FRAME
-
-					if (tx_status[snd_ch] == TX_TAIL)
-						bit = get_new_bit_tail(snd_ch, bit);
-
-					if (tx_status[snd_ch] == TX_FRAME)
-						bit = il2p_get_new_bit(snd_ch, bit);
-
-					// No nrzi for il2p
-
-					tribit = (tribit << 1) | bit;
-				}
-				else
-				{
-					// ax25/fx25
-
-					if (tx_status[snd_ch] == TX_DELAY)
-						bit = get_new_bit_delay(snd_ch, bit);
-					if (tx_status[snd_ch] == TX_TAIL)
-						bit = get_new_bit_tail(snd_ch, bit);
-					if (tx_status[snd_ch] == TX_FRAME)
-						bit = get_new_bit(snd_ch, bit);
-
-					tribit = (tribit << 1) | tx_nrzi(snd_ch, bit);
-				}
-			}
-			tribit = gray_8PSK[tribit & 7];
-
-			tx_8PSK[snd_ch] = (tx_8PSK[snd_ch] + tribit) & 7;
-			tx_8PSK_old_I[snd_ch] = tx_8PSK_I[snd_ch];
-			tx_8PSK_old_Q[snd_ch] = tx_8PSK_Q[snd_ch];
-
-			switch (tx_8PSK[snd_ch])
-			{
-			case 0:
-
-				tx_8PSK_I[snd_ch] = 0;
-				tx_8PSK_Q[snd_ch] = 1;
-				break;
-
-			case 1:
-
-				tx_8PSK_I[snd_ch] = COS45;
-				tx_8PSK_Q[snd_ch] = COS45;
-				break;
-
-			case 2:
-
-				tx_8PSK_I[snd_ch] = 1;
-				tx_8PSK_Q[snd_ch] = 0;
-				break;
-
-			case 3:
-
-				tx_8PSK_I[snd_ch] = COS45;
-				tx_8PSK_Q[snd_ch] = -COS45;
-				break;
-
-			case 4:
-
-				tx_8PSK_I[snd_ch] = 0;
-				tx_8PSK_Q[snd_ch] = -1;
-				break;
-
-			case 5:
-
-				tx_8PSK_I[snd_ch] = -COS45;
-				tx_8PSK_Q[snd_ch] = -COS45;
-				break;
-
-			case 6:
-
-				tx_8PSK_I[snd_ch] = -1;
-				tx_8PSK_Q[snd_ch] = 0;
-				break;
-
-			case 7:
-
-				tx_8PSK_I[snd_ch] = -COS45;
-				tx_8PSK_Q[snd_ch] = COS45;
-				break;
-
-			}
-
-			tx_8PSK_avg_I[snd_ch] = 0.5f*(tx_8PSK_old_I[snd_ch] + tx_8PSK_I[snd_ch]);
-			tx_8PSK_df_I[snd_ch] = 0.5f*(tx_8PSK_old_I[snd_ch] - tx_8PSK_I[snd_ch]);
-			tx_8PSK_avg_Q[snd_ch] = 0.5f*(tx_8PSK_old_Q[snd_ch] + tx_8PSK_Q[snd_ch]);
-			tx_8PSK_df_Q[snd_ch] = 0.5f*(tx_8PSK_old_Q[snd_ch] - tx_8PSK_Q[snd_ch]);
-		}
-					
-		if (modem_mode[snd_ch] == MODE_MPSK)
-		{
-			qbit = 0;
-
-			// get the bits for each of 4 carriers
-
-			for (i = 1; i <= 4; i++)
-			{
-				bit = 0;
-
-				if (tx_status[snd_ch] == TX_SILENCE)
-				{
-					tx_delay_cnt[snd_ch] = 0;
-					Debugprintf("Start TXD");
-					tx_status[snd_ch] = TX_DELAY;
-				}
-
-				if (tx_status[snd_ch] == TX_DELAY)
-					bit = get_new_bit_delay(snd_ch, bit);
-
-				if (tx_status[snd_ch] == TX_TAIL)
-					bit = get_new_bit_tail(snd_ch, bit);
-
-				if (tx_status[snd_ch] == TX_FRAME)
-					bit = get_new_bit(snd_ch, bit);
-
-				qbit = (qbit << 1) | bit;
-			}
-
-			tx_old_inv1[snd_ch] = tx_inv1[snd_ch];
-			tx_old_inv2[snd_ch] = tx_inv2[snd_ch];
-			tx_old_inv3[snd_ch] = tx_inv3[snd_ch];
-			tx_old_inv4[snd_ch] = tx_inv4[snd_ch];
-
-			if ((qbit & 8) == 0)
-				tx_inv1[snd_ch] = -tx_inv1[snd_ch];
-			if ((qbit & 4) == 0)
-				tx_inv2[snd_ch] = -tx_inv2[snd_ch];
-			if ((qbit & 2) == 0)
-				tx_inv3[snd_ch] = -tx_inv3[snd_ch];
-			if ((qbit & 1) == 0)
-				tx_inv4[snd_ch] = -tx_inv4[snd_ch];
-
-		}
-	}
-
-	if (tx_status[snd_ch] == TX_WAIT_BPF)
-		get_wait_bpf(snd_ch);
-
-	if (modem_mode[snd_ch] == MODE_FSK)
-		return amp * sinf(tx_osc[snd_ch]);
-
-	if (modem_mode[snd_ch] == MODE_BPSK)
-		return sinf(tx_osc[snd_ch]) * tx_bit_mod[snd_ch];
-
-	if (modem_mode[snd_ch] == MODE_QPSK || modem_mode[snd_ch] == MODE_8PSK || modem_mode[snd_ch] == MODE_PI4QPSK)
-		return sin(tx_osc[snd_ch]) * tx_I_mod[snd_ch] + cos(tx_osc[snd_ch]) * tx_Q_mod[snd_ch];
-
-	if (modem_mode[snd_ch] == MODE_MPSK)
-		return 0.35*(sinf(tx_osc1[snd_ch])*tx_bit1_mod[snd_ch] +
-			sinf(tx_osc2[snd_ch])*tx_bit2_mod[snd_ch] +
-			sinf(tx_osc3[snd_ch])*tx_bit3_mod[snd_ch] +
-			sinf(tx_osc4[snd_ch])*tx_bit4_mod[snd_ch]);
-
-	return 0.0f;
-}
-
-float make_samples_calib(UCHAR snd_ch, UCHAR tones)
-{
-	float amp, pi2, x, x1;
-
-	x1 = pi * tx_baudrate[snd_ch] / TX_Samplerate;
-	pi2 = 2 * pi / TX_Samplerate;
-
-	switch (tones)
-	{
-	case 1:
-
-		tx_last_bit[snd_ch] = 1;
-		break;
-
-	case 2:
-
-		tx_last_bit[snd_ch] = 0;
-		break;
-
-	case 3:
-
-		tx_bit_osc[snd_ch] = tx_bit_osc[snd_ch] + x1;
-
-		if (tx_bit_osc[snd_ch] > pi)
-		{
-			tx_bit_osc[snd_ch] = tx_bit_osc[snd_ch] - pi;
-			tx_last_bit[snd_ch] = tx_last_bit[snd_ch] ^ 1;
-		}
-		break;
-	}
-
-	amp = 1;
-
-	if (tx_baudrate[snd_ch] > 600)
-	{
-		if (tx_hitoneraisedb[snd_ch] < 0 && tx_last_bit[snd_ch] == 0)
-			amp = tx_hitoneraise[snd_ch];
-
-		if (tx_hitoneraisedb[snd_ch] > 0 && tx_last_bit[snd_ch] == 1)
-			amp = tx_hitoneraise[snd_ch];
-	}
-	
-	if (tx_last_bit[snd_ch] == 0)
-		x = pi2*(tx_freq[snd_ch] + 0.5f * tx_shift[snd_ch]);
-	else
-		x = pi2*(tx_freq[snd_ch] - 0.5f * tx_shift[snd_ch]);
-
-	tx_osc[snd_ch] = tx_osc[snd_ch] + x;
-	
-	if (tx_osc[snd_ch] > 2*pi)
-		tx_osc[snd_ch] = tx_osc[snd_ch] - 2 * pi;
-
-	return amp * sinf(tx_osc[snd_ch]);
-}
-
-int amplitude = 22000;
-
-void modulator(UCHAR snd_ch, int buf_size)
-{
-	// We feed samples to samplesink instead of buffering them
-
-	// I think this is the top of the TX hierarchy
-
-	int i;
-	short Sample;
-
-	if (calib_mode[snd_ch] > 0)
-	{
-		if (calib_mode[snd_ch] == 4)		// CWID
-		{
-			if (tx_status[snd_ch] == TX_SILENCE)
-			{
-				SoundIsPlaying = TRUE;
-				Debugprintf("Start CWID Chan %d", snd_ch);
-				RadioPTT(snd_ch, 1);
-
-				tx_status[snd_ch] = 6;
-			}
-
-			if (ARDOPSendToCard(snd_ch, SendSize) == 1)
-			{
-				// End of TX
-
-				tx_status[snd_ch] = TX_SILENCE;		// Stop TX
-				Flush();
-				RadioPTT(snd_ch, 0);
-				Debugprintf("End CWID");
-				calib_mode[snd_ch] = 0;
-			}
-			return;
-		}
-
-
-		if (tx_status[snd_ch] == TX_SILENCE)
-		{
-			SoundIsPlaying = TRUE;
-			Debugprintf("Start Calib Chan %d", snd_ch);
-			RadioPTT(snd_ch, 1);
-
-			tx_bit_osc[snd_ch] = 0;
-			tx_last_bit[snd_ch] = 0;
-	
-			// fill filter 
-
-			for (i = 0; i < tx_BPF_tap[snd_ch]; i++)
-				tx_prev_BPF_buf[snd_ch][buf_size + i] = make_samples_calib(snd_ch,calib_mode[snd_ch]);
-		}
-		tx_status[snd_ch] = TX_WAIT_BPF;
-	
-		for (i = 0; i < buf_size; i++)
-			tx_src_BPF_buf[snd_ch][i] = make_samples_calib(snd_ch, calib_mode[snd_ch]);
-
-		FIR_filter(tx_src_BPF_buf[snd_ch],buf_size,tx_BPF_tap[snd_ch],tx_BPF_core[snd_ch],tx_BPF_buf[snd_ch],tx_prev_BPF_buf[snd_ch]);
-    
-		for (i = 0; i < buf_size; i++)
-		{
-			Sample = tx_BPF_buf[snd_ch][i] * amplitude;
-			SampleSink(modemtoSoundLR[snd_ch], Sample);
-		}
-	}
-	else
-	{
-		if (tx_status[snd_ch] == TX_SILENCE)
-		{
-			if (fx25_mode[snd_ch] == FX25_MODE_TXRX)
-				tx_fx25_mode[snd_ch] = 1;
-			else
-				tx_fx25_mode[snd_ch] = 0;
-
-			tx_bit_osc[snd_ch] = 0;
-			tx_8PSK[snd_ch] = 0;
-			tx_QPSK[snd_ch] = 0;
-			tx_last_bit[snd_ch] = 0;
-			tx_inv1[snd_ch] = 1;
-			tx_inv2[snd_ch] = 1;
-			tx_inv3[snd_ch] = 1;
-			tx_inv4[snd_ch] = 1;
-			tx_8PSK_I[snd_ch] =  0;
-			tx_8PSK_Q[snd_ch] =  1;
-			tx_8PSK_old_I[snd_ch] =  0;
-			tx_8PSK_old_Q[snd_ch] =  1;
-			tx_QPSK_I[snd_ch] =  COS45;
-			tx_QPSK_Q[snd_ch] =  COS45;
-			tx_QPSK_old_I[snd_ch] =  COS45;
-			tx_QPSK_old_Q[snd_ch] =  COS45;
-
-			for (i = 0; i < tx_BPF_tap[snd_ch]; i++)
-				tx_prev_BPF_buf[snd_ch][buf_size+i] = make_samples(snd_ch, &tx_pol[snd_ch]);
-		}
-		
-		for (i = 0; i < buf_size; i++)
-			tx_src_BPF_buf[snd_ch][i] = make_samples(snd_ch, &tx_pol[snd_ch]);
-		
-		FIR_filter(tx_src_BPF_buf[snd_ch], buf_size, tx_BPF_tap[snd_ch], tx_BPF_core[snd_ch], tx_BPF_buf[snd_ch], tx_prev_BPF_buf[snd_ch]);
-
-		for (i = 0; i < buf_size; i++)
-		{
-			Sample = tx_BPF_buf[snd_ch][i] * 20000.0f;
-			SampleSink(modemtoSoundLR[snd_ch], Sample);
-		}
-	}
-}
-
-
diff --git a/ax25_pad2.h b/ax25_pad2.h
deleted file mode 100644
index c6dc17a..0000000
--- a/ax25_pad2.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*-------------------------------------------------------------------
- *
- * Name:	ax25_pad2.h
- *
- * Purpose:	Header file for using ax25_pad2.c
- *		ax25_pad dealt only with UI frames.
- *		This adds a facility for the other types: U, s, I.
- *
- *------------------------------------------------------------------*/
-
-#ifndef AX25_PAD2_H
-#define AX25_PAD2_H 1
-
-#include "ax25_pad.h"
-
-
-
-
-#if AX25MEMDEBUG	// to investigate a memory leak problem
-
-
-
-packet_t ax25_u_frame_debug (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, ax25_frame_type_t ftype, int pf, int pid, unsigned char *pinfo, int info_len, char *src_file, int src_line);
-
-packet_t ax25_s_frame_debug (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, ax25_frame_type_t ftype, int modulo, int nr, int pf, unsigned char *pinfo, int info_len, char *src_file, int src_line);
-
-packet_t ax25_i_frame_debug (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, int modulo, int nr, int ns, int pf, int pid, unsigned char *pinfo, int info_len, char *src_file, int src_line);
-
-
-#define ax25_u_frame(a,n,c,f,p,q,i,l) ax25_u_frame_debug(a,n,c,f,p,q,i,l,__FILE__,__LINE__)
-
-#define ax25_s_frame(a,n,c,f,m,r,p,i,l) ax25_s_frame_debug(a,n,c,f,m,r,p,i,l,__FILE__,__LINE__)
-
-#define ax25_i_frame(a,n,c,m,r,s,p,q,i,l) ax25_i_frame_debug(a,n,c,m,r,s,p,q,i,l,__FILE__,__LINE__)
-
-
-#else
-
-packet_t ax25_u_frame (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, ax25_frame_type_t ftype, int pf, int pid, unsigned char *pinfo, int info_len);
-
-packet_t ax25_s_frame (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, ax25_frame_type_t ftype, int modulo, int nr, int pf, unsigned char *pinfo, int info_len);
-
-packet_t ax25_i_frame (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, int modulo, int nr, int ns, int pf, int pid, unsigned char *pinfo, int info_len);
-
-
-#endif
-
-
-
-
-#endif /* AX25_PAD2_H */
-
-/* end ax25_pad2.h */
-
-
diff --git a/beacon.h b/beacon.h
deleted file mode 100644
index f7d2a56..0000000
--- a/beacon.h
+++ /dev/null
@@ -1,6 +0,0 @@
-
-/* beacon.h */
-
-void beacon_init (struct audio_s *pmodem, struct misc_config_s *pconfig, struct igate_config_s *pigate);
-
-void beacon_tracker_set_debug (int level);
diff --git a/cdigipeater.h b/cdigipeater.h
deleted file mode 100644
index 69a4b8c..0000000
--- a/cdigipeater.h
+++ /dev/null
@@ -1,62 +0,0 @@
-
-
-#ifndef CDIGIPEATER_H
-#define CDIGIPEATER_H 1
-
-#include "regex.h"
-
-#include "direwolf.h"		/* for MAX_CHANS */
-#include "ax25_pad.h"		/* for packet_t */
-#include "audio.h"		/* for radio channel properties */
-
-
-/*
- * Information required for Connected mode digipeating.
- *
- * The configuration file reader fills in this information
- * and it is passed to cdigipeater_init at application start up time.
- */
-
-
-struct cdigi_config_s {
-
-/*
- * Rules for each of the [from_chan][to_chan] combinations.
- */
-	int	enabled[MAX_CHANS][MAX_CHANS];	// Is it enabled for from/to pair?
-
-	int has_alias[MAX_CHANS][MAX_CHANS];	// If there was no alias in the config file,
-						// the structure below will not be set up
-						// properly and an attempt to use it could
-						// result in a crash.  (fixed v1.5)
-						// Not needed for [APRS] DIGIPEAT because
-						// the alias is mandatory there.
-	regex_t	alias[MAX_CHANS][MAX_CHANS];
-
-	char *cfilter_str[MAX_CHANS][MAX_CHANS];
-						// NULL or optional Packet Filter strings such as "t/m".
-};
-
-/*
- * Call once at application start up time.
- */
-
-extern void cdigipeater_init (struct audio_s *p_audio_config, struct cdigi_config_s *p_cdigi_config);
-
-/*
- * Call this for each packet received.
- * Suitable packets will be queued for transmission.
- */
-
-extern void cdigipeater (int from_chan, packet_t pp);
-
-
-/* Make statistics available. */
-
-int cdigipeater_get_count (int from_chan, int to_chan);
-
-
-#endif 
-
-/* end cdigipeater.h */
-
diff --git a/cm108.h b/cm108.h
deleted file mode 100644
index 2def77a..0000000
--- a/cm108.h
+++ /dev/null
@@ -1,5 +0,0 @@
-/* Dire Wolf cm108.h */
-
-extern void cm108_find_ptt (char *output_audio_device, char *ptt_device, int ptt_device_size);
-
-extern int cm108_set_gpio_pin (char *name, int num, int state);
\ No newline at end of file
diff --git a/config.h b/config.h
deleted file mode 100644
index 360ac49..0000000
--- a/config.h
+++ /dev/null
@@ -1,262 +0,0 @@
-
-/*----------------------------------------------------------------------------
- * 
- * Name:	config.h
- *
- * Purpose:	
- *
- * Description:	
- *
- *-----------------------------------------------------------------------------*/
-
-
-#ifndef CONFIG_H
-#define CONFIG_H 1
-
-#include "audio.h"		/* for struct audio_s */
-#include "digipeater.h"		/* for struct digi_config_s */
-#include "cdigipeater.h"		/* for struct cdigi_config_s */
-#include "aprs_tt.h"		/* for struct tt_config_s */
-#include "igate.h"		/* for struct igate_config_s */
-
-/*
- * All the leftovers.
- * This wasn't thought out.  It just happened.
- */
-
-enum beacon_type_e { BEACON_IGNORE, BEACON_POSITION, BEACON_OBJECT, BEACON_TRACKER, BEACON_CUSTOM, BEACON_IGATE };
-
-enum sendto_type_e { SENDTO_XMIT, SENDTO_IGATE, SENDTO_RECV };
-
-
-#define MAX_BEACONS 30
-#define MAX_KISS_TCP_PORTS (MAX_CHANS+1)
-
-struct misc_config_s {
-
-	int agwpe_port;		/* TCP Port number for the "AGW TCPIP Socket Interface" */
-
-	// Previously we allowed only a single TCP port for KISS.
-	// An increasing number of people want to run multiple radios.
-	// Unfortunately, most applications don't know how to deal with multi-radio TNCs.
-	// They ignore the channel on receive and always transmit to channel 0.
-	// Running multiple instances of direwolf is a work-around but this leads to
-	// more complex configuration and we lose the cross-channel digipeating capability.
-	// In release 1.7 we add a new feature to assign a single radio channel to a TCP port.
-	// e.g.
-	//	KISSPORT 8001		# default, all channels.  Radio channel = KISS channel.
-	//
-	//	KISSPORT 7000 0		# Only radio channel 0 for receive.
-	//				# Transmit to radio channel 0, ignoring KISS channel.
-	//
-	//	KISSPORT 7001 1		# Only radio channel 1 for receive.  KISS channel set to 0.
-	//				# Transmit to radio channel 1, ignoring KISS channel.
-
-	int kiss_port[MAX_KISS_TCP_PORTS];	/* TCP Port number for the "TCP KISS" protocol. */
-	int kiss_chan[MAX_KISS_TCP_PORTS];	/* Radio Channel number for this port or -1 for all.  */
-
-	int kiss_copy;		/* Data from network KISS client is copied to all others. */
-	int enable_kiss_pt;	/* Enable pseudo terminal for KISS. */
-				/* Want this to be off by default because it hangs */
-				/* after a while if nothing is reading from other end. */
-
-	char kiss_serial_port[20];
-				/* Serial port name for our end of the */
-				/* virtual null modem for native Windows apps. */
-				/* Version 1.5 add same capability for Linux. */
-
-	int kiss_serial_speed;	/* Speed, in bps, for the KISS serial port. */
-				/* If 0, just leave what was already there. */
-
-	int kiss_serial_poll;	/* When using Bluetooth KISS, the /dev/rfcomm0 device */
-				/* will appear and disappear as the remote application */
-				/* opens and closes the virtual COM port. */
-				/* When this is non-zero, we will check periodically to */
-				/* see if the device has appeared and we will open it. */
-
-	char gpsnmea_port[20];	/* Serial port name for reading NMEA sentences from GPS. */
-				/* e.g. COM22, /dev/ttyACM0 */
-
-	int gpsnmea_speed;	/* Speed for above, baud, default 4800. */
-
-	char gpsd_host[20];	/* Host for gpsd server. */
-				/* e.g. localhost, 192.168.1.2 */
-
-	int gpsd_port;		/* Port number for gpsd server. */
-				/* Default is  2947. */
-
-				
-	char waypoint_serial_port[20];	/* Serial port name for sending NMEA waypoint sentences */
-				/* to a GPS map display or other mapping application. */
-				/* e.g. COM22, /dev/ttyACM0 */
-				/* Currently no option for setting non-standard speed. */
-				/* This was done in 2014 and no one has complained yet. */
-
-	char waypoint_udp_hostname[80];	/* Destination host when using UDP. */
-
-	int waypoint_udp_portnum;	/* UDP port. */
-
-	int waypoint_formats;	/* Which sentence formats should be generated? */
-
-#define WPL_FORMAT_NMEA_GENERIC 0x01		/* N	$GPWPL */
-#define WPL_FORMAT_GARMIN       0x02		/* G	$PGRMW */
-#define WPL_FORMAT_MAGELLAN     0x04		/* M	$PMGNWPL */
-#define WPL_FORMAT_KENWOOD      0x08		/* K	$PKWDWPL */
-#define WPL_FORMAT_AIS          0x10		/* A	!AIVDM */
-
-
-	int log_daily_names;	/* True to generate new log file each day. */
-
-	char log_path[80];	/* Either directory or full file name depending on above. */
-
-	int dns_sd_enabled;	/* DNS Service Discovery announcement enabled. */
-	char dns_sd_name[64];	/* Name announced on dns-sd; defaults to "Dire Wolf on <hostname>" */
-
-	int sb_configured;	/* TRUE if SmartBeaconing is configured. */
-	int sb_fast_speed;	/* MPH */
-	int sb_fast_rate;	/* seconds */
-	int sb_slow_speed;	/* MPH */
-	int sb_slow_rate;	/* seconds */
-	int sb_turn_time;	/* seconds */
-	int sb_turn_angle;	/* degrees */
-	int sb_turn_slope;	/* degrees * MPH */
-
-// AX.25 connected mode.
-
-	int frack;		/* Number of seconds to wait for ack to transmission. */
-
-	int retry;		/* Number of times to retry before giving up. */
-
-	int paclen;		/* Max number of bytes in information part of frame. */
-
-	int maxframe_basic;	/* Max frames to send before ACK.  mod 8 "Window" size. */
-
-	int maxframe_extended;	/* Max frames to send before ACK.  mod 128 "Window" size. */
-
-	int maxv22;		/* Maximum number of unanswered SABME frames sent before */
-				/* switching to SABM.  This is to handle the case of an old */
-				/* TNC which simply ignores SABME rather than replying with FRMR. */
-
-	char **v20_addrs;	/* Stations known to understand only AX.25 v2.0 so we don't */
-				/* waste time trying v2.2 first. */
-
-	int v20_count;		/* Number of station addresses in array above. */
-
-	char **noxid_addrs;	/* Stations known not to understand XID command so don't */
-				/* waste time sending it and eventually giving up. */
-				/* AX.25 for Linux is the one known case, so far, where */
-				/* SABME is implemented but XID is not. */
-
-	int noxid_count;	/* Number of station addresses in array above. */
-
-
-// Beacons.
- 			
-	int num_beacons;	/* Number of beacons defined. */
-
-	struct beacon_s {
-
-	  enum beacon_type_e btype;	/* Position or object. */
-
-	  int lineno;		/* Line number from config file for later error messages. */
-
-	  enum sendto_type_e sendto_type;
-
-				/* SENDTO_XMIT	- Usually beacons go to a radio transmitter. */
-				/*		  chan, below is the channel number. */
-				/* SENDTO_IGATE	- Send to IGate, probably to announce my position */
-				/* 		  rather than relying on someone else to hear */
-				/* 		  me on the radio and report me. */
-				/* SENDTO_RECV	- Pretend this was heard on the specified */
-				/* 		  radio channel.  Mostly for testing. It is a */
-				/* 		  convenient way to send packets to attached apps. */
-
-	  int sendto_chan;	/* Transmit or simulated receive channel for above.  Should be 0 for IGate. */
-
-	  int delay;		/* Seconds to delay before first transmission. */
-
-	  int slot;		/* Seconds after hour for slotted time beacons. */
-				/* If specified, it overrides any 'delay' value. */
-
-	  int every;		/* Time between transmissions, seconds. */
-				/* Remains fixed for PBEACON and OBEACON. */
-				/* Dynamically adjusted for TBEACON. */
-
-	  time_t next;		/* Unix time to transmit next one. */
-
-	  char *source;		/* NULL or explicit AX.25 source address to use */
-				/* instead of the mycall value for the channel. */
-
-	  char *dest;		/* NULL or explicit AX.25 destination to use */
-				/* instead of the software version such as APDW11. */
-
-	  int compress;		/* Use more compact form? */
-
-	  char objname[10];	/* Object name.  Any printable characters. */
-
-	  char *via;		/* Path, e.g. "WIDE1-1,WIDE2-1" or NULL. */
-
-	  char *custom_info;	/* Info part for handcrafted custom beacon. */
-				/* Ignore the rest below if this is set. */
-
-	  char *custom_infocmd;	/* Command to generate info part. */
-				/* Again, other options below are then ignored. */
-
-	  int messaging;	/* Set messaging attribute for position report. */
-				/* i.e. Data Type Indicator of '=' rather than '!' */
-
-	  double lat;		/* Latitude and longitude. */
-	  double lon;
-	  int ambiguity;	/* Number of lower digits to trim from location. 0 (default), 1, 2, 3, 4. */
-	  float alt_m;		/* Altitude in meters. */
-
-	  char symtab;		/* Symbol table: / or \ or overlay character. */
-	  char symbol;		/* Symbol code. */
-
-	  float power;		/* For PHG. */
-	  float height;		/* HAAT in feet */
-	  float gain;		/* Original protocol spec was unclear. */
-				/* Addendum 1.1 clarifies it is dBi not dBd. */
-
-	  char dir[3];		/* 1 or 2 of N,E,W,S, or empty for omni. */
-
-	  float freq;		/* MHz. */
-	  float tone;		/* Hz. */
-	  float offset;		/* MHz. */
-	
-	  char *comment;	/* Comment or NULL. */
-	  char *commentcmd;	/* Command to append more to Comment or NULL. */
-
-
-	} beacon[MAX_BEACONS];
-
-};
-
-
-#define MIN_IP_PORT_NUMBER 1024
-#define MAX_IP_PORT_NUMBER 49151
-
-
-#define DEFAULT_AGWPE_PORT 8000		/* Like everyone else. */
-#define DEFAULT_KISS_PORT 8001		/* Above plus 1. */
-
-
-#define DEFAULT_NULLMODEM "COM3"  	/* should be equiv. to /dev/ttyS2 on Cygwin */
-
-
-
-
-extern void config_init (char *fname, struct audio_s *p_modem, 
-			struct digi_config_s *digi_config,
-			struct cdigi_config_s *cdigi_config,
-			struct tt_config_s *p_tt_config,
-			struct igate_config_s *p_igate_config,
-			struct misc_config_s *misc_config);
-
-
-
-#endif /* CONFIG_H */
-
-/* end config.h */
-
-
diff --git a/decode_aprs.h b/decode_aprs.h
deleted file mode 100644
index f25d1e9..0000000
--- a/decode_aprs.h
+++ /dev/null
@@ -1,150 +0,0 @@
-
-/* decode_aprs.h */
-
-
-#ifndef DECODE_APRS_H
-
-#define DECODE_APRS_H 1
-
-
-
-#ifndef G_UNKNOWN
-#include "latlong.h"
-#endif
-
-#ifndef AX25_MAX_ADDR_LEN
-#include "ax25_pad.h"
-#endif 
-
-#ifndef APRSTT_LOC_DESC_LEN
-#include "aprs_tt.h"
-#endif
-
-typedef struct decode_aprs_s {
-
-	int g_quiet;			/* Suppress error messages when decoding. */
-
-        char g_src[AX25_MAX_ADDR_LEN];
-
-        char g_dest[AX25_MAX_ADDR_LEN];
-
-        char g_data_type_desc[100];	/* APRS data type description.  Telemetry descriptions get pretty long. */
-
-        char g_symbol_table;		/* The Symbol Table Identifier character selects one */
-					/* of the two Symbol Tables, or it may be used as */
-					/* single-character (alpha or numeric) overlay, as follows: */
-					
-					/*	/ 	Primary Symbol Table (mostly stations) */
-
-					/* 	\ 	Alternate Symbol Table (mostly Objects) */
-
-					/*	0-9 	Numeric overlay. Symbol from Alternate Symbol */
-					/*		Table (uncompressed lat/long data format) */
-
-					/*	a-j	Numeric overlay. Symbol from Alternate */
-					/*		Symbol Table (compressed lat/long data */
-					/*		format only). i.e. a-j maps to 0-9 */
-
-					/*	A-Z	Alpha overlay. Symbol from Alternate Symbol Table */
-
-
-        char g_symbol_code;		/* Where the Symbol Table Identifier is 0-9 or A-Z (or a-j */
-					/* with compressed position data only), the symbol comes from */
-					/* the Alternate Symbol Table, and is overlaid with the */
-					/* identifier (as a single digit or a capital letter). */
-
-	char g_aprstt_loc[APRSTT_LOC_DESC_LEN];		/* APRStt location from !DAO! */
-
-        double g_lat, g_lon;		/* Location, degrees.  Negative for South or West. */
-					/* Set to G_UNKNOWN if missing or error. */
-
-        char g_maidenhead[12];		/* 4 or 6 (or 8?) character maidenhead locator. */
-
-        char g_name[12];		/* Object or item name. Max. 9 characters. */
-
-	char g_addressee[12];		/* Addressee for a "message."  Max. 9 characters. */
-					/* Also for Directed Station Query which is a */
-					/* special case of message. */
-
-	enum message_subtype_e { message_subtype_invalid = 0,
-				message_subtype_message,
-				message_subtype_ack,
-				message_subtype_rej,
-				message_subtype_telem_parm,
-				message_subtype_telem_unit,
-				message_subtype_telem_eqns,
-				message_subtype_telem_bits,
-				message_subtype_directed_query
-		} g_message_subtype;	/* Various cases of the overloaded "message." */
-
-	char g_message_number[12];	/* Message number.  Should be 1 - 5 alphanumeric characters if used. */
-					/* Addendum 1.1 has new format {mm} or {mm}aa with only two */
-					/* characters for message number and an ack riding piggyback. */
-
-        float g_speed_mph;		/* Speed in MPH.  */
-					/* The APRS transmission uses knots so watch out for */
-					/* conversions when sending and receiving APRS packets. */
-
-        float g_course;			/* 0 = North, 90 = East, etc. */
-	
-        int g_power;			/* Transmitter power in watts. */
-
-        int g_height;			/* Antenna height above average terrain, feet. */
-
-        int g_gain;			/* Antenna gain in dB. */
-
-        char g_directivity[12];		/* Direction of max signal strength */
-
-        float g_range;			/* Precomputed radio range in miles. */
-
-        float g_altitude_ft;		/* Feet above median sea level.  */
-					/* I used feet here because the APRS specification */
-					/* has units of feet for alititude.  Meters would be */
-					/* more natural to the other 96% of the world. */
-
-        char g_mfr[80];			/* Manufacturer or application. */
-
-        char g_mic_e_status[32];	/* MIC-E message. */
-
-        double g_freq;			/* Frequency, MHz */
-
-        float g_tone;			/* CTCSS tone, Hz, one fractional digit */
-
-        int g_dcs;			/* Digital coded squelch, print as 3 octal digits. */
-
-        int g_offset;			/* Transmit offset, kHz */
-
-
-	char g_query_type[12];		/* General Query: APRS, IGATE, WX, ... */
-					/* Addressee is NOT set. */
-
-					/* Directed Station Query: exactly 5 characters. */
-					/* APRSD, APRST, PING?, ... */
-					/* Addressee is set. */
-	
-	double g_footprint_lat;		/* A general query may contain a foot print. */
-	double g_footprint_lon;		/* Set all to G_UNKNOWN if not used. */
-	float g_footprint_radius;	/* Radius in miles. */
-
-	char g_query_callsign[12];	/* Directed query may contain callsign.  */
-					/* e.g. tell me all objects from that callsign. */
-
-
-        char g_weather[500];		/* Weather.  Can get quite long. Rethink max size. */
-
-        char g_telemetry[256];		/* Telemetry data.  Rethink max size. */
-
-        char g_comment[256];		/* Comment. */
-
-} decode_aprs_t;
-
-
-
-
-
-extern void decode_aprs (decode_aprs_t *A, packet_t pp, int quiet, char *third_party_src);
-
-extern void decode_aprs_print (decode_aprs_t *A);
-
-
-#endif
diff --git a/dedupe.h b/dedupe.h
deleted file mode 100644
index 9c0613c..0000000
--- a/dedupe.h
+++ /dev/null
@@ -1,10 +0,0 @@
-
-
-void dedupe_init (int ttl);
-
-void dedupe_remember (packet_t pp, int chan);
-
-int dedupe_check (packet_t pp, int chan);
-
-
-/* end dedupe.h */
diff --git a/demod.h b/demod.h
deleted file mode 100644
index 3233b9b..0000000
--- a/demod.h
+++ /dev/null
@@ -1,17 +0,0 @@
-
-
-/* demod.h */
-
-#include "audio.h" 	/* for struct audio_s */
-#include "ax25_pad.h"	/* for alevel_t */
-
-
-int demod_init (struct audio_s *pa);
-
-int demod_get_sample (int a);
-
-void demod_process_sample (int chan, int subchan, int sam);
-
-void demod_print_agc (int chan, int subchan);
-
-alevel_t demod_get_audio_level (int chan, int subchan);
\ No newline at end of file
diff --git a/demod_afsk.h b/demod_afsk.h
deleted file mode 100644
index e44a44e..0000000
--- a/demod_afsk.h
+++ /dev/null
@@ -1,8 +0,0 @@
-
-/* demod_afsk.h */
-
-
-void demod_afsk_init (int samples_per_sec, int baud, int mark_freq,
-			int space_freq, char profile, struct demodulator_state_s *D);
-
-void demod_afsk_process_sample (int chan, int subchan, int sam, struct demodulator_state_s *D);
diff --git a/demod_psk.h b/demod_psk.h
deleted file mode 100644
index 134b199..0000000
--- a/demod_psk.h
+++ /dev/null
@@ -1,7 +0,0 @@
-
-/* demod_psk.h */
-
-
-void demod_psk_init (enum modem_t modem_type, enum v26_e v26_alt, int samples_per_sec, int bps, char profile, struct demodulator_state_s *D);
-
-void demod_psk_process_sample (int chan, int subchan, int sam, struct demodulator_state_s *D);
diff --git a/digipeater.h b/digipeater.h
deleted file mode 100644
index 5c84976..0000000
--- a/digipeater.h
+++ /dev/null
@@ -1,78 +0,0 @@
-
-#ifndef DIGIPEATER_H
-#define DIGIPEATER_H 1
-
-#include "regex.h"
-
-#include "direwolf.h"		/* for MAX_CHANS */
-#include "ax25_pad.h"		/* for packet_t */
-#include "audio.h"		/* for radio channel properties */
-
-
-/*
- * Information required for digipeating.
- *
- * The configuration file reader fills in this information
- * and it is passed to digipeater_init at application start up time.
- */
-
-
-struct digi_config_s {
-
-
-	int	dedupe_time;	/* Don't digipeat duplicate packets */
-				/* within this number of seconds. */
-
-#define DEFAULT_DEDUPE 30
-
-/*
- * Rules for each of the [from_chan][to_chan] combinations.
- */
-
-	regex_t	alias[MAX_CHANS][MAX_CHANS];
-
-	regex_t	wide[MAX_CHANS][MAX_CHANS];
-
-	int	enabled[MAX_CHANS][MAX_CHANS];
-
-	enum preempt_e { PREEMPT_OFF, PREEMPT_DROP, PREEMPT_MARK, PREEMPT_TRACE } preempt[MAX_CHANS][MAX_CHANS];
-
-	// ATGP is an ugly hack for the specific need of ATGP which needs more that 8 digipeaters.
-	// DO NOT put this in the User Guide.  On a need to know basis.
-
-	char atgp[MAX_CHANS][MAX_CHANS][AX25_MAX_ADDR_LEN];
-
-	char *filter_str[MAX_CHANS+1][MAX_CHANS+1];
-						// NULL or optional Packet Filter strings such as "t/m".
-						// Notice the size of arrays is one larger than normal.
-						// That extra position is for the IGate.
-
-	int regen[MAX_CHANS][MAX_CHANS];	// Regenerate packet.  
-						// Sort of like digipeating but passed along unchanged.
-};
-
-/*
- * Call once at application start up time.
- */
-
-extern void digipeater_init (struct audio_s *p_audio_config, struct digi_config_s *p_digi_config);
-
-/*
- * Call this for each packet received.
- * Suitable packets will be queued for transmission.
- */
-
-extern void digipeater (int from_chan, packet_t pp);
-
-void digi_regen (int from_chan, packet_t pp);
-
-
-/* Make statistics available. */
-
-int digipeater_get_count (int from_chan, int to_chan);
-
-
-#endif 
-
-/* end digipeater.h */
-
diff --git a/dlq.h b/dlq.h
deleted file mode 100644
index 8771636..0000000
--- a/dlq.h
+++ /dev/null
@@ -1,148 +0,0 @@
-
-/*------------------------------------------------------------------
- *
- * Module:      dlq.h
- *
- *---------------------------------------------------------------*/
-
-#ifndef DLQ_H
-#define DLQ_H 1
-
-#include "ax25_pad.h"
-#include "audio.h"
-
-
-/* A transmit or receive data block for connected mode. */
-
-typedef struct cdata_s {
-	int magic;			/* For integrity checking. */
-
-#define TXDATA_MAGIC 0x09110911
-
-	struct cdata_s *next;		/* Pointer to next when part of a list. */
-
-	int pid;			/* Protocol id. */
-
-	int size;			/* Number of bytes allocated. */
-
-	int len;			/* Number of bytes actually used. */
-
-	char data[];			/* Variable length data. */
-
-} cdata_t;
-
-
-
-/* Types of things that can be in queue. */
-
-typedef enum dlq_type_e {DLQ_REC_FRAME, DLQ_CONNECT_REQUEST, DLQ_DISCONNECT_REQUEST, DLQ_XMIT_DATA_REQUEST, DLQ_REGISTER_CALLSIGN, DLQ_UNREGISTER_CALLSIGN, DLQ_OUTSTANDING_FRAMES_REQUEST, DLQ_CHANNEL_BUSY, DLQ_SEIZE_CONFIRM, DLQ_CLIENT_CLEANUP} dlq_type_t;
-
-
-/* A queue item. */
-
-// TODO: call this event rather than item.
-// TODO: should add fences.
-
-typedef struct dlq_item_s {
-
-	struct dlq_item_s *nextp;	/* Next item in queue. */
-
-	dlq_type_t type;		/* Type of item. */
-					/* See enum definition above. */
-
-	int chan;			/* Radio channel of origin. */
-
-// I'm not worried about amount of memory used but this might be a
-// little clearer if a union was used for the different event types.
-
-// Used for received frame.
-
-	int subchan;			/* Winning "subchannel" when using multiple */
-					/* decoders on one channel.  */
-					/* Special case, -1 means DTMF decoder. */
-					/* Maybe we should have a different type in this case? */
-
-	int slice;			/* Winning slicer. */
-
-	packet_t pp;			/* Pointer to frame structure. */
-
-	alevel_t alevel;		/* Audio level. */
-
-	int is_fx25;			/* Was it from FX.25? */
-
-	retry_t retries;		/* Effort expended to get a valid CRC. */
-					/* Bits changed for regular AX.25. */
-					/* Number of bytes fixed for FX.25. */
-
-	char spectrum[MAX_SUBCHANS*MAX_SLICERS+1];	/* "Spectrum" display for multi-decoders. */
-
-// Used by requests from a client application, connect, etc.
-
-	char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN];
-
-	int num_addr;			/* Range 2 .. 10. */
-
-	int client;
-
-
-// Used only by client request to transmit connected data.
-
-	cdata_t *txdata;
-
-// Used for channel activity change.
-// It is useful to know when the channel is busy either for carrier detect
-// or when we are transmitting.
-
-	int activity;			/* OCTYPE_PTT for my transmission start/end. */
-					/* OCTYPE_DCD if we hear someone else. */
-
-	int status;			/* 1 for active or 0 for quiet. */
-
-} dlq_item_t;
-
-
-
-void dlq_init (void);
-
-
-
-void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, int is_fx25, retry_t retries, char *spectrum);
-
-void dlq_connect_request (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, int chan, int client, int pid);
-
-void dlq_disconnect_request (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, int chan, int client);
-
-void dlq_outstanding_frames_request (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, int chan, int client);
-
-void dlq_xmit_data_request (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, int chan, int client, int pid, char *xdata_ptr, int xdata_len);
-
-void dlq_register_callsign (char addr[AX25_MAX_ADDR_LEN], int chan, int client);
-
-void dlq_unregister_callsign (char addr[AX25_MAX_ADDR_LEN], int chan, int client);
-
-void dlq_channel_busy (int chan, int activity, int status);
-
-void dlq_seize_confirm (int chan);
-
-void dlq_client_cleanup (int client);
-
-
-
-int dlq_wait_while_empty (double timeout_val);
-
-struct dlq_item_s *dlq_remove (void);
-
-void dlq_delete (struct dlq_item_s *pitem);
-
-
-
-cdata_t *cdata_new (int pid, char *data, int len);
-
-void cdata_delete (cdata_t *txdata);
-
-void cdata_check_leak (void);
-
-
-#endif
-
-/* end dlq.h */
diff --git a/dns_sd_common.h b/dns_sd_common.h
deleted file mode 100644
index f104bf8..0000000
--- a/dns_sd_common.h
+++ /dev/null
@@ -1,7 +0,0 @@
-
-#if (USE_AVAHI_CLIENT|USE_MACOS_DNSSD)
-
-char *dns_sd_default_service_name(void);
-
-#endif
-
diff --git a/dns_sd_dw.h b/dns_sd_dw.h
deleted file mode 100644
index 79f4b86..0000000
--- a/dns_sd_dw.h
+++ /dev/null
@@ -1,10 +0,0 @@
-
-#if (USE_AVAHI_CLIENT|USE_MACOS_DNSSD)
-
-#include "config.h"
-
-#define DNS_SD_SERVICE "_kiss-tnc._tcp"
-
-void dns_sd_announce (struct misc_config_s *mc);
-
-#endif // USE_AVAHI_CLIENT
diff --git a/dtime_now.h b/dtime_now.h
deleted file mode 100644
index 411534b..0000000
--- a/dtime_now.h
+++ /dev/null
@@ -1,18 +0,0 @@
-
-
-extern double dtime_realtime (void);
-
-extern double dtime_monotonic (void);
-
-
-void timestamp_now (char *result, int result_size, int show_ms);
-
-void timestamp_user_format (char *result, int result_size, char *user_format);
-
-void timestamp_filename (char *result, int result_size);
-
-
-// FIXME:  remove temp workaround.
-// Needs many scattered updates.
-
-#define dtime_now dtime_realtime
diff --git a/dtmf.h b/dtmf.h
deleted file mode 100644
index c1b52b9..0000000
--- a/dtmf.h
+++ /dev/null
@@ -1,14 +0,0 @@
-/* dtmf.h */
-
-
-#include "audio.h"
-
-void dtmf_init (struct audio_s *p_audio_config, int amp);
-
-char dtmf_sample (int c, float input);
-
-int dtmf_send (int chan, char *str, int speed, int txdelay, int txtail);
-
-
-/* end dtmf.h */
-
diff --git a/dwgps.h b/dwgps.h
deleted file mode 100644
index 78f821f..0000000
--- a/dwgps.h
+++ /dev/null
@@ -1,61 +0,0 @@
-
-/* dwgps.h */
-
-#ifndef DWGPS_H
-#define DWGPS_H 1
-
-
-#include <time.h>
-#include "config.h"	/* for struct misc_config_s */
-
-
-/*
- * Values for fix, equivalent to values from libgps.
- *	-2 = not initialized.
- *	-1 = error communicating with GPS receiver.
- *	0 = nothing heard yet.
- *	1 = had signal but lost it.
- *	2 = 2D.
- *	3 = 3D.
- *
- * Undefined float & double values are set to G_UNKNOWN.
- *
- */
-
-enum dwfix_e { DWFIX_NOT_INIT= -2, DWFIX_ERROR= -1, DWFIX_NOT_SEEN=0, DWFIX_NO_FIX=1, DWFIX_2D=2, DWFIX_3D=3 };
-
-typedef enum dwfix_e dwfix_t;
-
-typedef struct dwgps_info_s {
-	time_t timestamp;	/* When last updated.  System time. */
-	dwfix_t fix;		/* Quality of position fix. */
-	double dlat;		/* Latitude.  Valid if fix >= 2. */
-	double dlon;		/* Longitude. Valid if fix >= 2. */
-	float speed_knots;	/* libgps uses meters/sec but we use GPS usual knots. */
-	float track;		/* What is difference between track and course? */
-	float altitude;		/* meters above mean sea level. Valid if fix == 3. */
-} dwgps_info_t;
-
-
-
-
-
-void dwgps_init (struct misc_config_s *pconfig, int debug);
-
-void dwgps_clear (dwgps_info_t *gpsinfo);
-
-dwfix_t dwgps_read (dwgps_info_t *gpsinfo);
-
-void dwgps_print (char *msg, dwgps_info_t *gpsinfo);
-
-void dwgps_term (void);
-
-void dwgps_set_data (dwgps_info_t *gpsinfo);
-
-
-#endif /* DWGPS_H 1 */
-
-/* end dwgps.h */
-
-
-
diff --git a/dwgpsd.h b/dwgpsd.h
deleted file mode 100644
index 4c0e0fd..0000000
--- a/dwgpsd.h
+++ /dev/null
@@ -1,22 +0,0 @@
-
-/* dwgpsd.h   -   For communicating with daemon */
-
-
-
-#ifndef DWGPSD_H
-#define DWGPSD_H 1
-
-#include "config.h"
-
-
-int dwgpsd_init (struct misc_config_s *pconfig, int debug);
-
-void dwgpsd_term (void);
-
-#endif
-
-
-/* end dwgpsd.h */
-
-
-
diff --git a/dwgpsnmea.h b/dwgpsnmea.h
deleted file mode 100644
index ffe5a12..0000000
--- a/dwgpsnmea.h
+++ /dev/null
@@ -1,32 +0,0 @@
-
-/* dwgpsnmea.h   -   For reading NMEA sentences over serial port */
-
-
-
-#ifndef DWGPSNMEA_H
-#define DWGPSNMEA_H 1
-
-#include "dwgps.h"		/* for dwfix_t */
-#include "config.h"
-#include "serial_port.h"	/* for MYFDTYPE */
-
-
-int dwgpsnmea_init (struct misc_config_s *pconfig, int debug);
-
-MYFDTYPE dwgpsnmea_get_fd(char *wp_port_name, int speed);
-
-void dwgpsnmea_term (void);
-
-
-dwfix_t dwgpsnmea_gprmc (char *sentence, int quiet, double *odlat, double *odlon, float *oknots, float *ocourse);
-
-dwfix_t dwgpsnmea_gpgga (char *sentence, int quiet, double *odlat, double *odlon, float *oalt, int *onsat);
-
-
-#endif
-
-
-/* end dwgpsnmea.h */
-
-
-
diff --git a/dwsock.h b/dwsock.h
deleted file mode 100644
index 986f6a2..0000000
--- a/dwsock.h
+++ /dev/null
@@ -1,21 +0,0 @@
-
-/* dwsock.h - Socket helper functions. */
-
-#ifndef DWSOCK_H
-#define DWSOCK_H 1
-
-#define DWSOCK_IPADDR_LEN 48		// Size of string to hold IPv4 or IPv6 address.
-					// I think 40 would be adequate but we'll make
-					// it a little larger just to be safe.
-					// Use INET6_ADDRSTRLEN (from netinet/in.h) instead?
-
-int dwsock_init (void);
-
-int dwsock_connect (char *hostname, char *port, char *description, int allow_ipv6, int debug, char ipaddr_str[DWSOCK_IPADDR_LEN]);
-								/* ipaddr_str needs to be at least SOCK_IPADDR_LEN bytes */
-
-char *dwsock_ia_to_text (int  Family, void * pAddr, char * pStringBuf, size_t StringBufSize);
-
-void dwsock_close (int fd);
-
-#endif
\ No newline at end of file
diff --git a/encode_aprs.h b/encode_aprs.h
deleted file mode 100644
index dc7b8bd..0000000
--- a/encode_aprs.h
+++ /dev/null
@@ -1,17 +0,0 @@
-
-int encode_position (int messaging, int compressed, double lat, double lon, int ambiguity, int alt_ft,
-		char symtab, char symbol, 
-		int power, int height, int gain, char *dir,
-		int course, int speed_knots,
-		float freq, float tone, float offset,
-		char *comment,
-		char *presult, size_t result_size);
-
-int encode_object (char *name, int compressed, time_t thyme, double lat, double lon, int ambiguity,
-		char symtab, char symbol, 
-		int power, int height, int gain, char *dir,
-		int course, int speed_knots,
-		float freq, float tone, float offset, char *comment,
-		char *presult, size_t result_size);
-
-int encode_message (char *addressee, char *text, char *id, char *presult, size_t result_size);
diff --git a/fcs_calc.h b/fcs_calc.h
deleted file mode 100644
index 2e2b0ef..0000000
--- a/fcs_calc.h
+++ /dev/null
@@ -1,11 +0,0 @@
-
-/* fcs_calc.h */
-
-
-unsigned short fcs_calc (unsigned char *data, int len);
-
-unsigned short crc16 (unsigned char *data, int len, unsigned short seed);
-
-/* end fcs_calc.h */
-
-
diff --git a/fsk_filters.h b/fsk_filters.h
deleted file mode 100644
index 81c4e9a..0000000
--- a/fsk_filters.h
+++ /dev/null
@@ -1,7 +0,0 @@
-/* 1200 bits/sec with Audio sample rate = 11025 */
-/* Mark freq = 1200, Space freq = 2200 */
-
-static const signed short m_sin_table[9] = { 0 , 7347 , 11257 , 9899 , 3909 , -3909 , -9899 , -11257 , -7347  };
-static const signed short m_cos_table[9] = { 11431 , 8756 , 1984 , -5715 , -10741 , -10741 , -5715 , 1984 , 8756  };
-static const signed short s_sin_table[9] = { 0 , 10950 , 6281 , -7347 , -10496 , 1327 , 11257 , 5130 , -8314  };
-static const signed short s_cos_table[9] = { 11431 , 3278 , -9550 , -8756 , 4527 , 11353 , 1984 , -10215 , -7844  };
diff --git a/fsk_gen_filter.h b/fsk_gen_filter.h
deleted file mode 100644
index e7e8fa6..0000000
--- a/fsk_gen_filter.h
+++ /dev/null
@@ -1,15 +0,0 @@
-
-
-#ifndef FSK_GEN_FILTER_H
-#define FSK_GEN_FILTER_H 1
-
-#include "audio.h"
-#include "fsk_demod_state.h"
-
-void fsk_gen_filter (int samples_per_sec, 
-			int baud, 
-			int mark_freq, int space_freq, 
-			char profile,
-			struct demodulator_state_s *D);
-
-#endif
\ No newline at end of file
diff --git a/gen_tone.h b/gen_tone.h
deleted file mode 100644
index bbe23b5..0000000
--- a/gen_tone.h
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * gen_tone.h
- */
-
-
-int gen_tone_init (struct audio_s *pp, int amp, int gen_packets);
-
-
-//int gen_tone_open (int nchan, int sample_rate, int bit_rate, int f1, int f2, int amp, char *fname);
-
-//int gen_tone_open_fd (int nchan, int sample_rate, int bit_rate, int f1, int f2, int amp, int fd)  ;
-
-//int gen_tone_close (void);
-
-void tone_gen_put_bit (int chan, int dat);
-
-void gen_tone_put_sample (int chan, int a, int sam);
\ No newline at end of file
diff --git a/grm_sym.h b/grm_sym.h
deleted file mode 100644
index 7a15041..0000000
--- a/grm_sym.h
+++ /dev/null
@@ -1,501 +0,0 @@
-
-/*
- * grm_sym.h
- *
- * Symbol codes for use in $PGRMWPL sentence. 
- *
- * Copied from 
- *	Garmin Device Interface Specification
- *	May 19, 2006
- *	Drawing Number: 001-00063-00 Rev. C
- */
-
-
-typedef unsigned short symbol_type_t;
-
-enum symbol_type_e
-{
-/*---------------------------------------------------------------
-Marine symbols
----------------------------------------------------------------*/
-sym_anchor = 0, /* white anchor symbol */
-sym_bell = 1, /* white bell symbol */
-sym_diamond_grn = 2, /* green diamond symbol */
-sym_diamond_red = 3, /* red diamond symbol */
-sym_dive1 = 4, /* diver down flag 1 */
-sym_dive2 = 5, /* diver down flag 2 */
-sym_dollar = 6, /* white dollar symbol */
-sym_fish = 7, /* white fish symbol */
-sym_fuel = 8, /* white fuel symbol */
-sym_horn = 9, /* white horn symbol */
-sym_house = 10, /* white house symbol */
-sym_knife = 11, /* white knife & fork symbol */
-sym_light = 12, /* white light symbol */
-sym_mug = 13, /* white mug symbol */
-sym_skull = 14, /* white skull and crossbones symbol*/
-sym_square_grn = 15, /* green square symbol */
-sym_square_red = 16, /* red square symbol */
-sym_wbuoy = 17, /* white buoy waypoint symbol */
-sym_wpt_dot = 18, /* waypoint dot */
-sym_wreck = 19, /* white wreck symbol */
-sym_null = 20, /* null symbol (transparent) */
-sym_mob = 21, /* man overboard symbol */
-sym_buoy_ambr = 22, /* amber map buoy symbol */
-sym_buoy_blck = 23, /* black map buoy symbol */
-sym_buoy_blue = 24, /* blue map buoy symbol */
-sym_buoy_grn = 25, /* green map buoy symbol */
-sym_buoy_grn_red = 26, /* green/red map buoy symbol */
-sym_buoy_grn_wht = 27, /* green/white map buoy symbol */
-sym_buoy_orng = 28, /* orange map buoy symbol */
-sym_buoy_red = 29, /* red map buoy symbol */
-sym_buoy_red_grn = 30, /* red/green map buoy symbol */
-sym_buoy_red_wht = 31, /* red/white map buoy symbol */
-sym_buoy_violet = 32, /* violet map buoy symbol */
-sym_buoy_wht = 33, /* white map buoy symbol */
-sym_buoy_wht_grn = 34, /* white/green map buoy symbol */
-sym_buoy_wht_red = 35, /* white/red map buoy symbol */
-sym_dot = 36, /* white dot symbol */
-sym_rbcn = 37, /* radio beacon symbol */
-sym_boat_ramp = 150, /* boat ramp symbol */
-sym_camp = 151, /* campground symbol */
-sym_restrooms = 152, /* restrooms symbol */
-sym_showers = 153, /* shower symbol */
-sym_drinking_wtr = 154, /* drinking water symbol */
-sym_phone = 155, /* telephone symbol */
-sym_1st_aid = 156, /* first aid symbol */
-sym_info = 157, /* information symbol */
-sym_parking = 158, /* parking symbol */
-sym_park = 159, /* park symbol */
-sym_picnic = 160, /* picnic symbol */
-sym_scenic = 161, /* scenic area symbol */
-sym_skiing = 162, /* skiing symbol */
-sym_swimming = 163, /* swimming symbol */
-sym_dam = 164, /* dam symbol */
-sym_controlled = 165, /* controlled area symbol */
-sym_danger = 166, /* danger symbol */
-sym_restricted = 167, /* restricted area symbol */
-sym_null_2 = 168, /* null symbol */
-sym_ball = 169, /* ball symbol */
-sym_car = 170, /* car symbol */
-sym_deer = 171, /* deer symbol */
-sym_shpng_cart = 172, /* shopping cart symbol */
-sym_lodging = 173, /* lodging symbol */
-sym_mine = 174, /* mine symbol */
-sym_trail_head = 175, /* trail head symbol */
-sym_truck_stop = 176, /* truck stop symbol */
-sym_user_exit = 177, /* user exit symbol */
-sym_flag = 178, /* flag symbol */
-sym_circle_x = 179, /* circle with x in the center */
-sym_open_24hr = 180, /* open 24 hours symbol */
-sym_fhs_facility = 181, /* U Fishing Hot Spots(tm) Facility */
-sym_bot_cond = 182, /* Bottom Conditions */
-sym_tide_pred_stn = 183, /* Tide/Current Prediction Station */
-sym_anchor_prohib = 184, /* U anchor prohibited symbol */
-sym_beacon = 185, /* U beacon symbol */
-sym_coast_guard = 186, /* U coast guard symbol */
-sym_reef = 187, /* U reef symbol */
-sym_weedbed = 188, /* U weedbed symbol */
-sym_dropoff = 189, /* U dropoff symbol */
-sym_dock = 190, /* U dock symbol */
-sym_marina = 191, /* U marina symbol */
-sym_bait_tackle = 192, /* U bait and tackle symbol */
-sym_stump = 193, /* U stump symbol */
-/*---------------------------------------------------------------
-User customizable symbols
-The values from sym_begin_custom to sym_end_custom inclusive are
-reserved for the identification of user customizable symbols.
----------------------------------------------------------------*/
-sym_begin_custom = 7680, /* first user customizable symbol */
-sym_end_custom = 8191, /* last user customizable symbol */
-/*---------------------------------------------------------------
-Land symbols
----------------------------------------------------------------*/
-sym_is_hwy = 8192, /* interstate hwy symbol */
-sym_us_hwy = 8193, /* us hwy symbol */
-sym_st_hwy = 8194, /* state hwy symbol */
-sym_mi_mrkr = 8195, /* mile marker symbol */
-sym_trcbck = 8196, /* TracBack (feet) symbol */
-sym_golf = 8197, /* golf symbol */
-sym_sml_cty = 8198, /* small city symbol */
-sym_med_cty = 8199, /* medium city symbol */
-sym_lrg_cty = 8200, /* large city symbol */
-sym_freeway = 8201, /* intl freeway hwy symbol */
-sym_ntl_hwy = 8202, /* intl national hwy symbol */
-sym_cap_cty = 8203, /* capitol city symbol (star) */
-sym_amuse_pk = 8204, /* amusement park symbol */
-sym_bowling = 8205, /* bowling symbol */
-sym_car_rental = 8206, /* car rental symbol */
-sym_car_repair = 8207, /* car repair symbol */
-sym_fastfood = 8208, /* fast food symbol */
-sym_fitness = 8209, /* fitness symbol */
-sym_movie = 8210, /* movie symbol */
-sym_museum = 8211, /* museum symbol */
-sym_pharmacy = 8212, /* pharmacy symbol */
-sym_pizza = 8213, /* pizza symbol */
-sym_post_ofc = 8214, /* post office symbol */
-sym_rv_park = 8215, /* RV park symbol */
-sym_school = 8216, /* school symbol */
-sym_stadium = 8217, /* stadium symbol */
-sym_store = 8218, /* dept. store symbol */
-sym_zoo = 8219, /* zoo symbol */
-sym_gas_plus = 8220, /* convenience store symbol */
-sym_faces = 8221, /* live theater symbol */
-sym_ramp_int = 8222, /* ramp intersection symbol */
-sym_st_int = 8223, /* street intersection symbol */
-sym_weigh_sttn = 8226, /* inspection/weigh station symbol */
-sym_toll_booth = 8227, /* toll booth symbol */
-sym_elev_pt = 8228, /* elevation point symbol */
-sym_ex_no_srvc = 8229, /* exit without services symbol */
-sym_geo_place_mm = 8230, /* Geographic place name, man-made */
-sym_geo_place_wtr = 8231, /* Geographic place name, water */
-sym_geo_place_lnd = 8232, /* Geographic place name, land */
-sym_bridge = 8233, /* bridge symbol */
-sym_building = 8234, /* building symbol */
-sym_cemetery = 8235, /* cemetery symbol */
-sym_church = 8236, /* church symbol */
-sym_civil = 8237, /* civil location symbol */
-sym_crossing = 8238, /* crossing symbol */
-sym_hist_town = 8239, /* historical town symbol */
-sym_levee = 8240, /* levee symbol */
-sym_military = 8241, /* military location symbol */
-sym_oil_field = 8242, /* oil field symbol */
-sym_tunnel = 8243, /* tunnel symbol */
-sym_beach = 8244, /* beach symbol */
-sym_forest = 8245, /* forest symbol */
-sym_summit = 8246, /* summit symbol */
-sym_lrg_ramp_int = 8247, /* large ramp intersection symbol */
-sym_lrg_ex_no_srvc = 8248, /* large exit without services smbl */
-sym_badge = 8249, /* police/official badge symbol */
-sym_cards = 8250, /* gambling/casino symbol */
-sym_snowski = 8251, /* snow skiing symbol */
-sym_iceskate = 8252, /* ice skating symbol */
-sym_wrecker = 8253, /* tow truck (wrecker) symbol */
-sym_border = 8254, /* border crossing (port of entry) */
-sym_geocache = 8255, /* geocache location */
-sym_geocache_fnd = 8256, /* found geocache */
-sym_cntct_smiley = 8257, /* Rino contact symbol, "smiley" */
-sym_cntct_ball_cap = 8258, /* Rino contact symbol, "ball cap" */
-sym_cntct_big_ears = 8259, /* Rino contact symbol, "big ear" */
-sym_cntct_spike = 8260, /* Rino contact symbol, "spike" */
-sym_cntct_goatee = 8261, /* Rino contact symbol, "goatee" */
-sym_cntct_afro = 8262, /* Rino contact symbol, "afro" */
-sym_cntct_dreads = 8263, /* Rino contact symbol, "dreads" */
-sym_cntct_female1 = 8264, /* Rino contact symbol, "female 1" */
-sym_cntct_female2 = 8265, /* Rino contact symbol, "female 2" */
-sym_cntct_female3 = 8266, /* Rino contact symbol, "female 3" */
-sym_cntct_ranger = 8267, /* Rino contact symbol, "ranger" */
-sym_cntct_kung_fu = 8268, /* Rino contact symbol, "kung fu" */
-sym_cntct_sumo = 8269, /* Rino contact symbol, "sumo" */
-sym_cntct_pirate = 8270, /* Rino contact symbol, "pirate" */
-sym_cntct_biker = 8271, /* Rino contact symbol, "biker" */
-sym_cntct_alien = 8272, /* Rino contact symbol, "alien" */
-sym_cntct_bug = 8273, /* Rino contact symbol, "bug" */
-sym_cntct_cat = 8274, /* Rino contact symbol, "cat" */
-sym_cntct_dog = 8275, /* Rino contact symbol, "dog" */
-sym_cntct_pig = 8276, /* Rino contact symbol, "pig" */
-sym_hydrant = 8282, /* water hydrant symbol */
-sym_flag_blue = 8284, /* blue flag symbol */
-sym_flag_green = 8285, /* green flag symbol */
-sym_flag_red = 8286, /* red flag symbol */
-sym_pin_blue = 8287, /* blue pin symbol */
-sym_pin_green = 8288, /* green pin symbol */
-sym_pin_red = 8289, /* red pin symbol */
-sym_block_blue = 8290, /* blue block symbol */
-sym_block_green = 8291, /* green block symbol */
-sym_block_red = 8292, /* red block symbol */
-sym_bike_trail = 8293, /* bike trail symbol */
-sym_circle_red = 8294, /* red circle symbol */
-sym_circle_green = 8295, /* green circle symbol */
-sym_circle_blue = 8296, /* blue circle symbol */
-sym_diamond_blue = 8299, /* blue diamond symbol */
-sym_oval_red = 8300, /* red oval symbol */
-sym_oval_green = 8301, /* green oval symbol */
-sym_oval_blue = 8302, /* blue oval symbol */
-sym_rect_red = 8303, /* red rectangle symbol */
-sym_rect_green = 8304, /* green rectangle symbol */
-sym_rect_blue = 8305, /* blue rectangle symbol */
-sym_square_blue = 8308, /* blue square symbol */
-sym_letter_a_red = 8309, /* red letter 'A' symbol */
-sym_letter_b_red = 8310, /* red letter 'B' symbol */
-sym_letter_c_red = 8311, /* red letter 'C' symbol */
-sym_letter_d_red = 8312, /* red letter 'D' symbol */
-sym_letter_a_green = 8313, /* green letter 'A' symbol */
-sym_letter_c_green = 8314, /* green letter 'C' symbol */
-sym_letter_b_green = 8315, /* green letter 'B' symbol */
-sym_letter_d_green = 8316, /* green letter 'D' symbol */
-sym_letter_a_blue = 8317, /* blue letter 'A' symbol */
-sym_letter_b_blue = 8318, /* blue letter 'B' symbol */
-sym_letter_c_blue = 8319, /* blue letter 'C' symbol */
-sym_letter_d_blue = 8320, /* blue letter 'D' symbol */
-sym_number_0_red = 8321, /* red number '0' symbol */
-sym_number_1_red = 8322, /* red number '1' symbol */
-sym_number_2_red = 8323, /* red number '2' symbol */
-sym_number_3_red = 8324, /* red number '3' symbol */
-sym_number_4_red = 8325, /* red number '4' symbol */
-sym_number_5_red = 8326, /* red number '5' symbol */
-sym_number_6_red = 8327, /* red number '6' symbol */
-sym_number_7_red = 8328, /* red number '7' symbol */
-sym_number_8_red = 8329, /* red number '8' symbol */
-sym_number_9_red = 8330, /* red number '9' symbol */
-sym_number_0_green = 8331, /* green number '0' symbol */
-sym_number_1_green = 8332, /* green number '1' symbol */
-sym_number_2_green = 8333, /* green number '2' symbol */
-sym_number_3_green = 8334, /* green number '3' symbol */
-sym_number_4_green = 8335, /* green number '4' symbol */
-sym_number_5_green = 8336, /* green number '5' symbol */
-sym_number_6_green = 8337, /* green number '6' symbol */
-sym_number_7_green = 8338, /* green number '7' symbol */
-sym_number_8_green = 8339, /* green number '8' symbol */
-sym_number_9_green = 8340, /* green number '9' symbol */
-sym_number_0_blue = 8341, /* blue number '0' symbol */
-sym_number_1_blue = 8342, /* blue number '1' symbol */
-sym_number_2_blue = 8343, /* blue number '2' symbol */
-sym_number_3_blue = 8344, /* blue number '3' symbol */
-sym_number_4_blue = 8345, /* blue number '4' symbol */
-sym_number_5_blue = 8346, /* blue number '5' symbol */
-sym_number_6_blue = 8347, /* blue number '6' symbol */
-sym_number_7_blue = 8348, /* blue number '7' symbol */
-sym_number_8_blue = 8349, /* blue number '8' symbol */
-sym_number_9_blue = 8350, /* blue number '9' symbol */
-sym_triangle_blue = 8351, /* blue triangle symbol */
-sym_triangle_green = 8352, /* green triangle symbol */
-sym_triangle_red = 8353, /* red triangle symbol */
-sym_food_asian = 8359, /* asian food symbol */
-sym_food_deli = 8360, /* deli symbol */
-sym_food_italian = 8361, /* italian food symbol */
-sym_food_seafood = 8362, /* seafood symbol */
-sym_food_steak = 8363, /* steak symbol */
-/*---------------------------------------------------------------
-Aviation symbols
----------------------------------------------------------------*/
-sym_airport = 16384, /* airport symbol */
-sym_int = 16385, /* intersection symbol */
-sym_ndb = 16386, /* non-directional beacon symbol */
-sym_vor = 16387, /* VHF omni-range symbol */
-sym_heliport = 16388, /* heliport symbol */
-sym_private = 16389, /* private field symbol */
-sym_soft_fld = 16390, /* soft field symbol */
-sym_tall_tower = 16391, /* tall tower symbol */
-sym_short_tower = 16392, /* short tower symbol */
-sym_glider = 16393, /* glider symbol */
-sym_ultralight = 16394, /* ultralight symbol */
-sym_parachute = 16395, /* parachute symbol */
-sym_vortac = 16396, /* VOR/TACAN symbol */
-sym_vordme = 16397, /* VOR-DME symbol */
-sym_faf = 16398, /* first approach fix */
-sym_lom = 16399, /* localizer outer marker */
-sym_map = 16400, /* missed approach point */
-sym_tacan = 16401, /* TACAN symbol */
-sym_seaplane = 16402, /* Seaplane Base */
-};
-
-
-
-/*
- * Mapping from APRS symbols to Garmin.
- */
-
-// TODO:  NEEDS MORE WORK!!!
-
-
-#define SYMTAB_SIZE 95
-
-#define sym_default sym_diamond_grn
-
-
-static const symbol_type_t grm_primary_symtab[SYMTAB_SIZE] =  {
-
-	sym_default,		//     00  	 --no-symbol--
-	sym_cntct_ranger,	//  !  01  	 Police, Sheriff
-	sym_default,		//  "  02  	 reserved  (was rain)
-	sym_rbcn,		//  #  03  	 DIGI (white center)
-	sym_phone,		//  $  04  	 PHONE
-	sym_rbcn,		//  %  05  	 DX CLUSTER
-	sym_rbcn,		//  &  06  	 HF GATEway
-	sym_glider,		//  '  07  	 Small AIRCRAFT
-	sym_rbcn,		//  (  08  	 Mobile Satellite Station
-	sym_default,		//  )  09  	 Wheelchair (handicapped)
-	sym_car,		//  *  10  	 SnowMobile
-	sym_1st_aid,		//  +  11  	 Red Cross
-	sym_cntct_ball_cap,	//  ,  12  	 Boy Scouts
-	sym_house,		//  -  13  	 House QTH (VHF)
-	sym_default,		//  .  14  	 X
-	sym_default,		//  /  15  	 Red Dot
-	sym_default,		//  0  16  	 # circle (obsolete)
-	sym_default,		//  1  17  	 TBD
-	sym_default,		//  2  18  	 TBD
-	sym_default,		//  3  19  	 TBD
-	sym_default,		//  4  20  	 TBD
-	sym_default,		//  5  21  	 TBD
-	sym_default,		//  6  22  	 TBD
-	sym_default,		//  7  23  	 TBD
-	sym_default,		//  8  24  	 TBD
-	sym_default,		//  9  25  	 TBD
-	sym_default,		//  :  26  	 FIRE
-	sym_camp,		//  ;  27  	 Campground (Portable ops)
-	sym_cntct_biker,	//  <  28  	 Motorcycle
-	sym_default,		//  =  29  	 RAILROAD ENGINE
-	sym_car,		//  >  30  	 CAR
-	sym_default,		//  ?  31  	 SERVER for Files
-	sym_default,		//  @  32  	 HC FUTURE predict (dot)
-	sym_1st_aid,		//  A  33  	 Aid Station
-	sym_rbcn,		//  B  34  	 BBS or PBBS
-	sym_boat_ramp,		//  C  35  	 Canoe
-	sym_default,		//  D  36  	 
-	sym_default,		//  E  37  	 EYEBALL (Eye catcher!)
-	sym_default,		//  F  38  	 Farm Vehicle (tractor)
-	sym_default,		//  G  39  	 Grid Square (6 digit)
-	sym_lodging,		//  H  40  	 HOTEL (blue bed symbol)
-	sym_rbcn,		//  I  41  	 TcpIp on air network stn
-	sym_default,		//  J  42  	 
-	sym_school,		//  K  43  	 School
-	sym_default,		//  L  44  	 PC user
-	sym_default,		//  M  45  	 MacAPRS
-	sym_default,		//  N  46  	 NTS Station
-	sym_parachute,		//  O  47  	 BALLOON
-	sym_cntct_ranger,	//  P  48  	 Police
-	sym_default,		//  Q  49  	 TBD
-	sym_rv_park,		//  R  50  	 REC. VEHICLE
-	sym_glider,		//  S  51  	 SHUTTLE
-	sym_default,		//  T  52  	 SSTV
-	sym_car,		//  U  53  	 BUS
-	sym_cntct_biker,	//  V  54  	 ATV
-	sym_default,		//  W  55  	 National WX Service Site
-	sym_default,		//  X  56  	 HELO
-	sym_default,		//  Y  57  	 YACHT (sail)
-	sym_default,		//  Z  58  	 WinAPRS
-	sym_cntct_smiley,	//  [  59  	 Human/Person (HT)
-	sym_triangle_green,	//  \  60  	 TRIANGLE(DF station)
-	sym_default,		//  ]  61  	 MAIL/PostOffice(was PBBS)
-	sym_glider,		//  ^  62  	 LARGE AIRCRAFT
-	sym_default,		//  _  63  	 WEATHER Station (blue)
-	sym_rbcn,		//  `  64  	 Dish Antenna
-	sym_1st_aid,		//  a  65  	 AMBULANCE
-	sym_cntct_biker,	//  b  66  	 BIKE
-	sym_default,		//  c  67  	 Incident Command Post
-	sym_hydrant,		//  d  68  	 Fire dept
-	sym_deer,		//  e  69  	 HORSE (equestrian)
-	sym_hydrant,		//  f  70  	 FIRE TRUCK
-	sym_glider,		//  g  71  	 Glider
-	sym_1st_aid,		//  h  72  	 HOSPITAL
-	sym_default,		//  i  73  	 IOTA (islands on the air)
-	sym_car,		//  j  74  	 JEEP
-	sym_car,		//  k  75  	 TRUCK
-	sym_default,		//  l  76  	 Laptop
-	sym_rbcn,		//  m  77  	 Mic-E Repeater
-	sym_default,		//  n  78  	 Node (black bulls-eye)
-	sym_default,		//  o  79  	 EOC
-	sym_cntct_dog,		//  p  80  	 ROVER (puppy, or dog)
-	sym_default,		//  q  81  	 GRID SQ shown above 128 m
-	sym_rbcn,		//  r  82  	 Repeater
-	sym_default,		//  s  83  	 SHIP (pwr boat)
-	sym_truck_stop,		//  t  84  	 TRUCK STOP
-	sym_truck_stop,		//  u  85  	 TRUCK (18 wheeler)
-	sym_car,		//  v  86  	 VAN
-	sym_drinking_wtr,	//  w  87  	 WATER station
-	sym_default,		//  x  88  	 xAPRS (Unix)
-	sym_tall_tower,		//  y  89  	 YAGI @ QTH
-	sym_default,		//  z  90  	 TBD
-	sym_default,		//  {  91  	 
-	sym_default,		//  |  92  	 TNC Stream Switch
-	sym_default,		//  }  93  	 
-	sym_default };		//  ~  94  	 TNC Stream Switch
-
-static const symbol_type_t grm_alternate_symtab[SYMTAB_SIZE] =  {
-
-	sym_default,		//     00  	 --no-symbol--
-	sym_default,		//  !  01  	 EMERGENCY (!)
-	sym_default,		//  "  02  	 reserved
-	sym_default,		//  #  03  	 OVERLAY DIGI (green star)
-	sym_default,		//  $  04  	 Bank or ATM  (green box)
-	sym_default,		//  %  05  	 Power Plant with overlay
-	sym_rbcn,		//  &  06  	 I=Igte IGate R=RX T=1hopTX 2=2hopTX
-	sym_default,		//  '  07  	 Crash (& now Incident sites)
-	sym_default,		//  (  08  	 CLOUDY (other clouds w ovrly)
-	sym_hydrant,		//  )  09  	 Firenet MEO, MODIS Earth Obs.
-	sym_default,		//  *  10  	 SNOW (& future ovrly codes)
-	sym_default,		//  +  11  	 Church
-	sym_cntct_female1,	//  ,  12  	 Girl Scouts
-	sym_house,		//  -  13  	 House (H=HF) (O = Op Present)
-	sym_default,		//  .  14  	 Ambiguous (Big Question mark)
-	sym_default,		//  /  15  	 Waypoint Destination
-	sym_default,		//  0  16  	 CIRCLE (E/I/W=IRLP/Echolink/WIRES)
-	sym_default,		//  1  17  	 
-	sym_default,		//  2  18  	 
-	sym_default,		//  3  19  	
-	sym_default,		//  4  20  
-	sym_default,		//  5  21 
-	sym_default,		//  6  22
-	sym_default,		//  7  23
-	sym_default,		//  8  24  	 802.11 or other network node
-	sym_default,		//  9  25  	 Gas Station (blue pump)
-	sym_default,		//  :  26  	 Hail (& future ovrly codes)
-	sym_park,		//  ;  27  	 Park/Picnic area
-	sym_default,		//  <  28  	 ADVISORY (one WX flag)
-	sym_rbcn,		//  =  29  	 APRStt Touchtone (DTMF users)
-	sym_car,		//  >  30  	 OVERLAID CAR
-	sym_default,		//  ?  31  	 INFO Kiosk  (Blue box with ?)
-	sym_default,		//  @  32  	 HURRICANE/Trop-Storm
-	sym_default,		//  A  33  	 overlayBOX DTMF & RFID & XO
-	sym_default,		//  B  34  	 Blwng Snow (& future codes)
-	sym_coast_guard,	//  C  35  	 Coast Guard
-	sym_default,		//  D  36  	 Drizzle (proposed APRStt)
-	sym_default,		//  E  37  	 Smoke (& other vis codes)
-	sym_default,		//  F  38  	 Freezng rain (&future codes)
-	sym_default,		//  G  39  	 Snow Shwr (& future ovrlys)
-	sym_default,		//  H  40  	 Haze (& Overlay Hazards)
-	sym_default,		//  I  41  	 Rain Shower
-	sym_default,		//  J  42  	 Lightning (& future ovrlys)
-	sym_rbcn,		//  K  43  	 Kenwood HT (W)
-	sym_light,		//  L  44  	 Lighthouse
-	sym_default,		//  M  45  	 MARS (A=Army,N=Navy,F=AF)
-	sym_default,		//  N  46  	 Navigation Buoy
-	sym_default,		//  O  47  	 Rocket
-	sym_default,		//  P  48  	 Parking
-	sym_default,		//  Q  49  	 QUAKE
-	sym_default,		//  R  50  	 Restaurant
-	sym_rbcn,		//  S  51  	 Satellite/Pacsat
-	sym_default,		//  T  52  	 Thunderstorm
-	sym_default,		//  U  53  	 SUNNY
-	sym_default,		//  V  54  	 VORTAC Nav Aid
-	sym_default,		//  W  55  	 # NWS site (NWS options)
-	sym_pharmacy,		//  X  56  	 Pharmacy Rx (Apothicary)
-	sym_rbcn,		//  Y  57  	 Radios and devices
-	sym_default,		//  Z  58  	 
-	sym_default,		//  [  59  	 W.Cloud (& humans w Ovrly)
-	sym_default,		//  \  60  	 New overlayable GPS symbol
-	sym_default,		//  ]  61  	 
-	sym_glider,		//  ^  62  	 # Aircraft (shows heading)
-	sym_default,		//  _  63  	 # WX site (green digi)
-	sym_default,		//  `  64  	 Rain (all types w ovrly)
-	sym_default,		//  a  65  	 ARRL, ARES, WinLINK
-	sym_default,		//  b  66  	 Blwng Dst/Snd (& others)
-	sym_default,		//  c  67  	 CD triangle RACES/SATERN/etc
-	sym_default,		//  d  68  	 DX spot by callsign
-	sym_default,		//  e  69  	 Sleet (& future ovrly codes)
-	sym_default,		//  f  70  	 Funnel Cloud
-	sym_default,		//  g  71  	 Gale Flags
-	sym_default,		//  h  72  	 Store. or HAMFST Hh=HAM store
-	sym_default,		//  i  73  	 BOX or points of Interest
-	sym_default,		//  j  74  	 WorkZone (Steam Shovel)
-	sym_car,		//  k  75  	 Special Vehicle SUV,ATV,4x4
-	sym_default,		//  l  76  	 Areas      (box,circles,etc)
-	sym_default,		//  m  77  	 Value Sign (3 digit display)
-	sym_default,		//  n  78  	 OVERLAY TRIANGLE
-	sym_default,		//  o  79  	 small circle
-	sym_default,		//  p  80  	 Prtly Cldy (& future ovrlys)
-	sym_default,		//  q  81  	 
-	sym_restrooms,		//  r  82  	 Restrooms
-	sym_default,		//  s  83  	 OVERLAY SHIP/boat (top view)
-	sym_default,		//  t  84  	 Tornado
-	sym_car,		//  u  85  	 OVERLAID TRUCK
-	sym_car,		//  v  86  	 OVERLAID Van
-	sym_default,		//  w  87  	 Flooding
-	sym_wreck,		//  x  88  	 Wreck or Obstruction ->X<-
-	sym_default,		//  y  89  	 Skywarn
-	sym_default,		//  z  90  	 OVERLAID Shelter
-	sym_default,		//  {  91  	 Fog (& future ovrly codes)
-	sym_default,		//  |  92  	 TNC Stream Switch
-	sym_default,		//  }  93  	 
-	sym_default };		//  ~  94  	 TNC Stream Switch
-
diff --git a/hdlc_send.h b/hdlc_send.h
deleted file mode 100644
index 4f8a105..0000000
--- a/hdlc_send.h
+++ /dev/null
@@ -1,17 +0,0 @@
-
-/* hdlc_send.h */
-
-// In version 1.7 an extra layer of abstraction was added here.
-// Rather than calling hdlc_send_frame, we now use another function
-// which sends AX.25, FX.25, or IL2P depending on
-
-#include "ax25_pad.h"
-#include "audio.h"
-
-int layer2_send_frame (int chan, packet_t pp, int bad_fcs, struct audio_s *audio_config_p);
-
-int layer2_preamble_postamble (int chan, int flags, int finish, struct audio_s *audio_config_p);
-
-/* end hdlc_send.h */
-
-
diff --git a/igate.h b/igate.h
deleted file mode 100644
index 8203ac7..0000000
--- a/igate.h
+++ /dev/null
@@ -1,128 +0,0 @@
-
-/*----------------------------------------------------------------------------
- * 
- * Name:	igate.h
- *
- * Purpose:	Interface to the Internet Gateway functions.
- *
- *-----------------------------------------------------------------------------*/
-
-
-#ifndef IGATE_H
-#define IGATE_H 1
-
-
-#include "ax25_pad.h"
-#include "digipeater.h"
-#include "audio.h"
-
-
-#define DEFAULT_IGATE_PORT 14580
-
-
-
-struct igate_config_s {
-
-/*
- * For logging into the IGate server.
- */
-	char t2_server_name[40];	/* Tier 2 IGate server name. */
-
-	int t2_server_port;		/* Typically 14580. */
-
-	char t2_login[AX25_MAX_ADDR_LEN];/* e.g. WA9XYZ-15 */
-					/* Note that the ssid could be any two alphanumeric */
-					/* characters not just 1 thru 15. */
-					/* Could be same or different than the radio call(s). */
-					/* Not sure what the consequences would be. */
-
-	char t2_passcode[8];		/* Max. 5 digits. Could be "-1". */
-
-	char *t2_filter;		/* Optional filter for IS -> RF direction. */
-					/* This is the "server side" filter. */
-					/* A better name would be subscription or something */
-					/* like that because we can only ask for more. */
-
-/*
- * For transmitting.
- */
-	int tx_chan;			/* Radio channel for transmitting. */
-					/* 0=first, etc.  -1 for none. */
-					/* Presently IGate can transmit on only a single channel. */
-					/* A future version might generalize this.  */
-					/* Each transmit channel would have its own client side filtering. */
-
-	char tx_via[80];		/* VIA path for transmitting third party packets. */
-					/* Usual text representation.  */
-					/* Must start with "," if not empty so it can */
-					/* simply be inserted after the destination address. */
-
-	int max_digi_hops;		/* Maximum number of digipeater hops possible for via path. */
-					/* Derived from the SSID when last character of address is a digit. */
-					/* e.g.  "WIDE1-1,WIDE5-2" would be 3. */
-					/* This is useful to know so we can determine how many */
-					/* stations we might be able to reach. */
-
-	int tx_limit_1;			/* Max. packets to transmit in 1 minute. */
-
-	int tx_limit_5;			/* Max. packets to transmit in 5 minutes. */
-
-	int igmsp;			/* Number of message sender position reports to allow. */
-					/* Common practice is to default to 1.  */
-					/* We allow additional flexibility of 0 to disable feature */
-					/* or a small number to allow more. */
-
-/*
- * Receiver to IS data options.
- */
-	int rx2ig_dedupe_time;		/* seconds.  0 to disable. */
-
-/*
- * Special SATgate mode to delay packets heard directly.
- */
-	int satgate_delay;		/* seconds.  0 to disable. */
-};
-
-
-#define IGATE_TX_LIMIT_1_DEFAULT 6
-#define IGATE_TX_LIMIT_1_MAX     20
-
-#define IGATE_TX_LIMIT_5_DEFAULT 20
-#define IGATE_TX_LIMIT_5_MAX     80
-
-#define IGATE_RX2IG_DEDUPE_TIME 0		/* Issue 85.  0 means disable dupe checking in RF>IS direction. */
-						/* See comments in rx_to_ig_remember & rx_to_ig_allow. */
-						/* Currently there is no configuration setting to change this. */
-
-#define DEFAULT_SATGATE_DELAY 10
-#define MIN_SATGATE_DELAY 5
-#define MAX_SATGATE_DELAY 30
-
-
-/* Call this once at startup */
-
-void igate_init (struct audio_s *p_audio_config, struct igate_config_s *p_igate_config, struct digi_config_s *p_digi_config, int debug_level);
-
-/* Call this with each packet received from the radio. */
-
-void igate_send_rec_packet (int chan, packet_t recv_pp);
-
-/* This when digipeater transmits.  Set bydigi to 1 . */
-
-void ig_to_tx_remember (packet_t pp, int chan, int bydigi);
-
-
-
-/* Get statistics for IGATE status beacon. */
-
-int igate_get_msg_cnt (void);
-
-int igate_get_pkt_cnt (void);
-
-int igate_get_upl_cnt (void);
-
-int igate_get_dnl_cnt (void);
-
-
-
-#endif
diff --git a/il2p.c.bak b/il2p.c.bak
deleted file mode 100644
index 2c81201..0000000
--- a/il2p.c.bak
+++ /dev/null
@@ -1,4502 +0,0 @@
-/*
-Copyright (C) 2019-2020 Andrei Kopanchuk UZ7HO
-
-This file is part of QtSoundModem
-
-QtSoundModem is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-QtSoundModem is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with QtSoundModem.  If not, see http://www.gnu.org/licenses
-
-*/
-
-// UZ7HO Soundmodem Port by John Wiseman G8BPQ
-
-// IL2P code. Based on Direwolf code, under the following copyright
-
-//
-//    Copyright (C) 2021  John Langner, WB2OSZ
-//
-//    This program is free software: you can redistribute it and/or modify
-//    it under the terms of the GNU General Public License as published by
-//    the Free Software Foundation, either version 2 of the License, or
-//    (at your option) any later version.
-//
-//    This program is distributed in the hope that it will be useful,
-//    but WITHOUT ANY WARRANTY; without even the implied warranty of
-//    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-//    GNU General Public License for more details.
-//
-//    You should have received a copy of the GNU General Public License
-//    along with this program.  If not, see <http://www.gnu.org/licenses/>.
-//
-
-
-// IP2P receive code (il2p_rec_bit) is called from the bit receiving code in ax25_demod.c, so includes parallel decoders
-
-
-
-
-#include "UZ7HOStuff.h"
-
-void Debugprintf(const char * format, ...);
-
-#define MAX_ADEVS 3			
-
-#define MAX_RADIO_CHANS ((MAX_ADEVS) * 2)
-
-#define MAX_CHANS MAX_RADIO_CHANS	// TODO: Replace all former  with latter to avoid confusion with following.
-
-#define MAX_TOTAL_CHANS 16		// v1.7 allows additional virtual channels which are connected
- // to something other than radio modems.
- // Total maximum channels is based on the 4 bit KISS field.
- // Someone with very unusual requirements could increase this and
- // use only the AGW network protocol.
-
-
-#define MAX_SUBCHANS 9
-
-#define MAX_SLICERS 9
-
-#define max(x, y) ((x) > (y) ? (x) : (y))
-#define min(x, y) ((x) < (y) ? (x) : (y))
-
-/* For option to try fixing frames with bad CRC. */
-
-typedef enum retry_e {
-	RETRY_NONE = 0,
-	RETRY_INVERT_SINGLE = 1,
-	RETRY_INVERT_DOUBLE = 2,
-	RETRY_INVERT_TRIPLE = 3,
-	RETRY_INVERT_TWO_SEP = 4,
-	RETRY_MAX = 5
-}  retry_t;
-
-typedef struct alevel_s {
-	int rec;
-	int mark;
-	int space;
-	//float ms_ratio;	// TODO: take out after temporary investigation.
-} alevel_t;
-
-
-alevel_t demod_get_audio_level(int chan, int subchan);
-void tone_gen_put_bit(int chan, int dat);
-
-int ax25memdebug = 1;
-
-// Code to try to determine centre freq
-
-float MagOut[4096];
-float MaxMagOut = 0;
-int MaxMagIndex = 0;
-
-// FFT Bin Size is 12000 / FFTSize
-
-#ifndef FX25_H
-#define FX25_H
-
-#include <stdint.h>	// for uint64_t
-
-
-/* Reed-Solomon codec control block */
-struct rs {
-	unsigned int mm;              /* Bits per symbol */
-	unsigned int nn;              /* Symbols per block (= (1<<mm)-1) */
-	unsigned char *alpha_to;      /* log lookup table */
-	unsigned char *index_of;      /* Antilog lookup table */
-	unsigned char *genpoly;       /* Generator polynomial */
-	unsigned int nroots;     /* Number of generator roots = number of parity symbols */
-	unsigned char fcr;        /* First consecutive root, index form */
-	unsigned char prim;       /* Primitive element, index form */
-	unsigned char iprim;      /* prim-th root of 1, index form */
-};
-
-#define MM (rs->mm)
-#define NN (rs->nn)
-#define ALPHA_TO (rs->alpha_to) 
-#define INDEX_OF (rs->index_of)
-#define GENPOLY (rs->genpoly)
-#define NROOTS (rs->nroots)
-#define FCR (rs->fcr)
-#define PRIM (rs->prim)
-#define IPRIM (rs->iprim)
-#define A0 (NN)
-
-int __builtin_popcountll(unsigned long long int i)
-{
-	return 0;
-}
-
-int __builtin_popcount(unsigned int n)
-{
-	unsigned int count = 0;
-	while (n)
-	{
-		count += n & 1;
-		n >>= 1;
-	}
-	return count;
-}
-
-static inline int modnn(struct rs *rs, int x) {
-	while (x >= rs->nn) {
-		x -= rs->nn;
-		x = (x >> rs->mm) + (x & rs->nn);
-	}
-	return x;
-}
-
-#define MODNN(x) modnn(rs,x)
-
-
-#define ENCODE_RS encode_rs_char
-#define DECODE_RS decode_rs_char
-#define INIT_RS init_rs_char
-#define FREE_RS free_rs_char
-
-#define DTYPE unsigned char
-
-void ENCODE_RS(struct rs *rs, DTYPE *data, DTYPE *bb);
-
-int DECODE_RS(struct rs *rs, DTYPE *data, int *eras_pos, int no_eras);
-
-struct rs *INIT_RS(unsigned int symsize, unsigned int gfpoly,
-	unsigned int fcr, unsigned int prim, unsigned int nroots);
-
-void FREE_RS(struct rs *rs);
-
-
-
-// These 3 are the external interface.
-// Maybe these should be in a different file, separated from the internal stuff.
-
-void fx25_init(int debug_level);
-int fx25_send_frame(int chan, unsigned char *fbuf, int flen, int fx_mode);
-void fx25_rec_bit(int chan, int subchan, int slice, int dbit);
-int fx25_rec_busy(int chan);
-
-
-// Other functions in fx25_init.c.
-
-struct rs *fx25_get_rs(int ctag_num);
-uint64_t fx25_get_ctag_value(int ctag_num);
-int fx25_get_k_data_radio(int ctag_num);
-int fx25_get_k_data_rs(int ctag_num);
-int fx25_get_nroots(int ctag_num);
-int fx25_get_debug(void);
-int fx25_tag_find_match(uint64_t t);
-int fx25_pick_mode(int fx_mode, int dlen);
-
-void fx_hex_dump(unsigned char *x, int len);
-
-/*-------------------------------------------------------------------
- *
- * Name:	ax25_pad.h
- *
- * Purpose:	Header file for using ax25_pad.c
- *
- *------------------------------------------------------------------*/
-
-#ifndef AX25_PAD_H
-#define AX25_PAD_H 1
-
-
-#define AX25_MAX_REPEATERS 8
-#define AX25_MIN_ADDRS 2	/* Destination & Source. */
-#define AX25_MAX_ADDRS 10	/* Destination, Source, 8 digipeaters. */	
-
-#define AX25_DESTINATION  0	/* Address positions in frame. */
-#define AX25_SOURCE       1	
-#define AX25_REPEATER_1   2
-#define AX25_REPEATER_2   3
-#define AX25_REPEATER_3   4
-#define AX25_REPEATER_4   5
-#define AX25_REPEATER_5   6
-#define AX25_REPEATER_6   7
-#define AX25_REPEATER_7   8
-#define AX25_REPEATER_8   9
-
-#define AX25_MAX_ADDR_LEN 12	/* In theory, you would expect the maximum length */
- /* to be 6 letters, dash, 2 digits, and nul for a */
- /* total of 10.  However, object labels can be 10 */
- /* characters so throw in a couple extra bytes */
- /* to be safe. */
-
-#define AX25_MIN_INFO_LEN 0	/* Previously 1 when considering only APRS. */
-
-#define AX25_MAX_INFO_LEN 2048	/* Maximum size for APRS. */
-				/* AX.25 starts out with 256 as the default max */
-				/* length but the end stations can negotiate */
-				/* something different. */
-				/* version 0.8:  Change from 256 to 2028 to */
-				/* handle the larger paclen for Linux AX25. */
-
-				/* These don't include the 2 bytes for the */
-				/* HDLC frame FCS. */
-
-/*
- * Previously, for APRS only.
- * #define AX25_MIN_PACKET_LEN ( 2 * 7 + 2 + AX25_MIN_INFO_LEN)
- * #define AX25_MAX_PACKET_LEN ( AX25_MAX_ADDRS * 7 + 2 + AX25_MAX_INFO_LEN)
- */
-
- /* The more general case. */
- /* An AX.25 frame can have a control byte and no protocol. */
-
-#define AX25_MIN_PACKET_LEN ( 2 * 7 + 1 )
-
-#define AX25_MAX_PACKET_LEN ( AX25_MAX_ADDRS * 7 + 2 + 3 + AX25_MAX_INFO_LEN)
-
-
-/*
- * packet_t is a pointer to a packet object.
- *
- * The actual implementation is not visible outside ax25_pad.c.
- */
-
-#define AX25_UI_FRAME 3		/* Control field value. */
-
-#define AX25_PID_NO_LAYER_3 0xf0		/* protocol ID used for APRS */
-#define AX25_PID_SEGMENTATION_FRAGMENT 0x08
-#define AX25_PID_ESCAPE_CHARACTER 0xff
-
-struct packet_s {
-
-	int magic1;		/* for error checking. */
-
-	int seq;		/* unique sequence number for debugging. */
-
-	double release_time;	/* Time stamp in format returned by dtime_now(). */
-				/* When to release from the SATgate mode delay queue. */
-
-#define MAGIC 0x41583235
-
-	struct packet_s *nextp;	/* Pointer to next in queue. */
-
-	int num_addr;		/* Number of addresses in frame. */
-				/* Range of AX25_MIN_ADDRS .. AX25_MAX_ADDRS for AX.25. */
-				/* It will be 0 if it doesn't look like AX.25. */
-				/* -1 is used temporarily at allocation to mean */
-				/* not determined yet. */
-
-
-
-				/*
-				 * The 7th octet of each address contains:
-					 *
-				 * Bits:   H  R  R  SSID  0
-				 *
-				 *   H 		for digipeaters set to 0 initially.
-				 *		Changed to 1 when position has been used.
-				 *
-				 *		for source & destination it is called
-				 *		command/response.  Normally both 1 for APRS.
-				 *		They should be opposites for connected mode.
-				 *
-				 *   R	R	Reserved.  Normally set to 1 1.
-				 *
-				 *   SSID	Substation ID.  Range of 0 - 15.
-				 *
-				 *   0		Usually 0 but 1 for last address.
-				 */
-
-
-#define SSID_H_MASK	0x80
-#define SSID_H_SHIFT	7
-
-#define SSID_RR_MASK	0x60
-#define SSID_RR_SHIFT	5
-
-#define SSID_SSID_MASK	0x1e
-#define SSID_SSID_SHIFT	1
-
-#define SSID_LAST_MASK	0x01
-
-
-	int frame_len;		/* Frame length without CRC. */
-
-	int modulo;		/* I & S frames have sequence numbers of either 3 bits (modulo 8) */
-				/* or 7 bits (modulo 128).  This is conveyed by either 1 or 2 */
-				/* control bytes.  Unfortunately, we can't determine this by looking */
-				/* at an isolated frame.  We need to know about the context.  If we */
-				/* are part of the conversation, we would know.  But if we are */
-				/* just listening to others, this would be more difficult to determine. */
-
-				/* For U frames:   	set to 0 - not applicable */
-				/* For I & S frames:	8 or 128 if known.  0 if unknown. */
-
-	unsigned char frame_data[AX25_MAX_PACKET_LEN + 1];
-	/* Raw frame contents, without the CRC. */
-
-
-	int magic2;		/* Will get stomped on if above overflows. */
-};
-
-
-
-typedef struct packet_s *packet_t;
-
-typedef enum cmdres_e { cr_00 = 2, cr_cmd = 1, cr_res = 0, cr_11 = 3 } cmdres_t;
-
-
-extern packet_t ax25_new(void);
-
-
-#ifdef AX25_PAD_C	/* Keep this hidden - implementation could change. */
-
-
-/*
- * APRS always has one control octet of 0x03 but the more
- * general AX.25 case is one or two control bytes depending on
- * whether "modulo 128 operation" is in effect.
- */
-
- //#define DEBUGX 1
-
-static inline int ax25_get_control_offset(packet_t this_p)
-{
-	return (this_p->num_addr * 7);
-}
-
-static inline int ax25_get_num_control(packet_t this_p)
-{
-	int c;
-
-	c = this_p->frame_data[ax25_get_control_offset(this_p)];
-
-	if ((c & 0x01) == 0) {			/* I   xxxx xxx0 */
-#if DEBUGX
-		Debugprintf("ax25_get_num_control, %02x is I frame, returns %d\n", c, (this_p->modulo == 128) ? 2 : 1);
-#endif
-		return ((this_p->modulo == 128) ? 2 : 1);
-	}
-
-	if ((c & 0x03) == 1) {			/* S   xxxx xx01 */
-#if DEBUGX
-		Debugprintf("ax25_get_num_control, %02x is S frame, returns %d\n", c, (this_p->modulo == 128) ? 2 : 1);
-#endif
-		return ((this_p->modulo == 128) ? 2 : 1);
-	}
-
-#if DEBUGX
-	Debugprintf("ax25_get_num_control, %02x is U frame, always returns 1.\n", c);
-#endif
-
-	return (1);					/* U   xxxx xx11 */
-}
-
-
-
-/*
- * APRS always has one protocol octet of 0xF0 meaning no level 3
- * protocol but the more general case is 0, 1 or 2 protocol ID octets.
- */
-
-static inline int ax25_get_pid_offset(packet_t this_p)
-{
-	return (ax25_get_control_offset(this_p) + ax25_get_num_control(this_p));
-}
-
-static int ax25_get_num_pid(packet_t this_p)
-{
-	int c;
-	int pid;
-
-	c = this_p->frame_data[ax25_get_control_offset(this_p)];
-
-	if ((c & 0x01) == 0 ||				/* I   xxxx xxx0 */
-		c == 0x03 || c == 0x13) {			/* UI  000x 0011 */
-
-		pid = this_p->frame_data[ax25_get_pid_offset(this_p)];
-#if DEBUGX
-		Debugprintf("ax25_get_num_pid, %02x is I or UI frame, pid = %02x, returns %d\n", c, pid, (pid == AX25_PID_ESCAPE_CHARACTER) ? 2 : 1);
-#endif
-		if (pid == AX25_PID_ESCAPE_CHARACTER) {
-			return (2);			/* pid 1111 1111 means another follows. */
-		}
-		return (1);
-	}
-#if DEBUGX
-	Debugprintf("ax25_get_num_pid, %02x is neither I nor UI frame, returns 0\n", c);
-#endif
-	return (0);
-}
-
-
-/*
- * AX.25 has info field for 5 frame types depending on the control field.
- *
- *	xxxx xxx0	I
- *	000x 0011	UI		(which includes APRS)
- *	101x 1111	XID
- *	111x 0011	TEST
- *	100x 0111	FRMR
- *
- * APRS always has an Information field with at least one octet for the Data Type Indicator.
- */
-
-static inline int ax25_get_info_offset(packet_t this_p)
-{
-	int offset = ax25_get_control_offset(this_p) + ax25_get_num_control(this_p) + ax25_get_num_pid(this_p);
-#if DEBUGX
-	Debugprintf("ax25_get_info_offset, returns %d\n", offset);
-#endif
-	return (offset);
-}
-
-static inline int ax25_get_num_info(packet_t this_p)
-{
-	int len;
-
-	/* assuming AX.25 frame. */
-
-	len = this_p->frame_len - this_p->num_addr * 7 - ax25_get_num_control(this_p) - ax25_get_num_pid(this_p);
-	if (len < 0) {
-		len = 0;		/* print error? */
-	}
-
-	return (len);
-}
-
-#endif
-
-
-typedef enum ax25_modulo_e { modulo_unknown = 0, modulo_8 = 8, modulo_128 = 128 } ax25_modulo_t;
-
-typedef enum ax25_frame_type_e {
-
-	frame_type_I = 0,	// Information
-
-	frame_type_S_RR,	// Receive Ready - System Ready To Receive
-	frame_type_S_RNR,	// Receive Not Ready - TNC Buffer Full
-	frame_type_S_REJ,	// Reject Frame - Out of Sequence or Duplicate
-	frame_type_S_SREJ,	// Selective Reject - Request single frame repeat
-
-	frame_type_U_SABME,	// Set Async Balanced Mode, Extended
-	frame_type_U_SABM,	// Set Async Balanced Mode
-	frame_type_U_DISC,	// Disconnect
-	frame_type_U_DM,	// Disconnect Mode
-	frame_type_U_UA,	// Unnumbered Acknowledge
-	frame_type_U_FRMR,	// Frame Reject
-	frame_type_U_UI,	// Unnumbered Information
-	frame_type_U_XID,	// Exchange Identification
-	frame_type_U_TEST,	// Test
-	frame_type_U,		// other Unnumbered, not used by AX.25.
-
-	frame_not_AX25		// Could not get control byte from frame.
-				// This must be last because value plus 1 is
-				// for the size of an array.
-
-} ax25_frame_type_t;
-
-
-/*
- * Originally this was a single number.
- * Let's try something new in version 1.2.
- * Also collect AGC values from the mark and space filters.
- */
-
-#ifndef AXTEST
-// TODO: remove this?
-#define AX25MEMDEBUG 1
-#endif
-
-
-
-extern packet_t ax25_from_text(char *monitor, int strict);
-
-extern packet_t ax25_from_frame(unsigned char *data, int len, alevel_t alevel);
-
-extern packet_t ax25_dup(packet_t copy_from);
-
-extern void ax25_delete(packet_t pp);
-
-
-
-extern int ax25_parse_addr(int position, char *in_addr, int strict, char *out_addr, int *out_ssid, int *out_heard);
-extern int ax25_check_addresses(packet_t pp);
-
-extern packet_t ax25_unwrap_third_party(packet_t from_pp);
-
-extern void ax25_set_addr(packet_t pp, int, char *);
-extern void ax25_insert_addr(packet_t this_p, int n, char *ad);
-extern void ax25_remove_addr(packet_t this_p, int n);
-
-extern int ax25_get_num_addr(packet_t pp);
-extern int ax25_get_num_repeaters(packet_t this_p);
-
-extern void ax25_get_addr_with_ssid(packet_t pp, int n, char *station);
-extern void ax25_get_addr_no_ssid(packet_t pp, int n, char *station);
-
-extern int ax25_get_ssid(packet_t pp, int n);
-extern void ax25_set_ssid(packet_t this_p, int n, int ssid);
-
-extern int ax25_get_h(packet_t pp, int n);
-
-extern void ax25_set_h(packet_t pp, int n);
-
-extern int ax25_get_heard(packet_t this_p);
-
-extern int ax25_get_first_not_repeated(packet_t pp);
-
-extern int ax25_get_rr(packet_t this_p, int n);
-
-extern int ax25_get_info(packet_t pp, unsigned char **paddr);
-extern void ax25_set_info(packet_t pp, unsigned char *info_ptr, int info_len);
-extern int ax25_cut_at_crlf(packet_t this_p);
-
-extern void ax25_set_nextp(packet_t this_p, packet_t next_p);
-
-extern int ax25_get_dti(packet_t this_p);
-
-extern packet_t ax25_get_nextp(packet_t this_p);
-
-extern void ax25_set_release_time(packet_t this_p, double release_time);
-extern double ax25_get_release_time(packet_t this_p);
-
-extern void ax25_set_modulo(packet_t this_p, int modulo);
-extern int ax25_get_modulo(packet_t this_p);
-
-extern void ax25_format_addrs(packet_t pp, char *);
-extern void ax25_format_via_path(packet_t this_p, char *result, size_t result_size);
-
-extern int ax25_pack(packet_t pp, unsigned char result[AX25_MAX_PACKET_LEN]);
-
-extern ax25_frame_type_t ax25_frame_type(packet_t this_p, cmdres_t *cr, char *desc, int *pf, int *nr, int *ns);
-
-extern void ax25_hex_dump(packet_t this_p);
-
-extern int ax25_is_aprs(packet_t pp);
-extern int ax25_is_null_frame(packet_t this_p);
-
-extern int ax25_get_control(packet_t this_p);
-extern int ax25_get_c2(packet_t this_p);
-
-extern int ax25_get_pid(packet_t this_p);
-
-extern int ax25_get_frame_len(packet_t this_p);
-extern unsigned char *ax25_get_frame_data_ptr(packet_t this_p);
-
-extern unsigned short ax25_dedupe_crc(packet_t pp);
-
-extern unsigned short ax25_m_m_crc(packet_t pp);
-
-extern void ax25_safe_print(char *, int, int ascii_only);
-
-#define AX25_ALEVEL_TO_TEXT_SIZE 40	// overkill but safe.
-extern int ax25_alevel_to_text(alevel_t alevel, char text[AX25_ALEVEL_TO_TEXT_SIZE]);
-
-
-#endif /* AX25_PAD_H */
-
-/* end ax25_pad.h */
-
-
-
-
-#define CTAG_MIN 0x01
-#define CTAG_MAX 0x0B
-
-// Maximum sizes of "data" and "check" parts.
-
-#define FX25_MAX_DATA 239	// i.e. RS(255,239)
-#define FX25_MAX_CHECK 64	// e.g. RS(255, 191)
-#define FX25_BLOCK_SIZE 255	// Block size always 255 for 8 bit symbols.
-
-#endif // FX25_H
-
-#ifndef IL2P_H
-#define IL2P_H 1
-
-
-#define IL2P_PREAMBLE 0x55
-
-#define IL2P_SYNC_WORD 0xF15E48
-
-#define IL2P_SYNC_WORD_SIZE 3
-#define IL2P_HEADER_SIZE 13	// Does not include 2 parity.
-#define IL2P_HEADER_PARITY 2
-
-#define IL2P_MAX_PAYLOAD_SIZE 1023
-#define IL2P_MAX_PAYLOAD_BLOCKS 5
-#define IL2P_MAX_PARITY_SYMBOLS 16		// For payload only.
-#define IL2P_MAX_ENCODED_PAYLOAD_SIZE (IL2P_MAX_PAYLOAD_SIZE + IL2P_MAX_PAYLOAD_BLOCKS * IL2P_MAX_PARITY_SYMBOLS)
-
-#define IL2P_MAX_PACKET_SIZE (IL2P_SYNC_WORD_SIZE + IL2P_HEADER_SIZE + IL2P_HEADER_PARITY + IL2P_MAX_ENCODED_PAYLOAD_SIZE)
-
-
-float GuessCentreFreq(int i)
-{
-	float Freq = 0;
-	float Start;
-	float End;
-	int n;
-	float Max = 0;
-	int Index = 0;
-
-	Start = (rx_freq[i] - RCVR[i] * rcvr_offset[i]) / BinSize;
-	End = (rx_freq[i] + RCVR[i] * rcvr_offset[i]) / BinSize;
-
-	for (n = Start; n <= End; n++)
-	{
-		if (MagOut[n] > Max)
-		{
-			Max = MagOut[n];
-			Index = n;
-		}
-	}
-
-	Freq = Index * BinSize;
-
-	return Freq;
-}
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_new
- *
- * Purpose:	Allocate memory for a new packet object.
- *
- * Returns:	Identifier for a new packet object.
- *		In the current implementation this happens to be a pointer.
- *
- *------------------------------------------------------------------------------*/
-
-int last_seq_num = 0;
-int new_count = 0;
-int delete_count = 0;
-
-packet_t ax25_new(void)
-{
-	struct packet_s *this_p;
-
-
-#if DEBUG 
-	text_color_set(DW_COLOR_DEBUG);
-	Debugprintf("ax25_new(): before alloc, new=%d, delete=%d\n", new_count, delete_count);
-#endif
-
-	last_seq_num++;
-	new_count++;
-
-	/*
-	 * check for memory leak.
-	 */
-
-	 // version 1.4 push up the threshold.   We could have considerably more with connected mode.
-
-		 //if (new_count > delete_count + 100) {
-	if (new_count > delete_count + 256) {
-
-		Debugprintf("Report to WB2OSZ - Memory leak for packet objects.  new=%d, delete=%d\n", new_count, delete_count);
-#if AX25MEMDEBUG
-#endif
-	}
-
-	this_p = calloc(sizeof(struct packet_s), (size_t)1);
-
-	if (this_p == NULL) {
-		Debugprintf("ERROR - can't allocate memory in ax25_new.\n");
-	}
-
-//	assert(this_p != NULL);
-
-	this_p->magic1 = MAGIC;
-	this_p->seq = last_seq_num;
-	this_p->magic2 = MAGIC;
-	this_p->num_addr = (-1);
-
-	return (this_p);
-}
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_delete
- *
- * Purpose:	Destroy a packet object, freeing up memory it was using.
- *
- *------------------------------------------------------------------------------*/
-
-void ax25_delete(packet_t this_p)
-{
-	if (this_p == NULL) {
-		Debugprintf("ERROR - NULL pointer passed to ax25_delete.\n");
-		return;
-	}
-
-	delete_count++;
-
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-	this_p->magic1 = 0;
-	this_p->magic1 = 0;
-
-	free(this_p);
-}
-
-
-
-
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_s_frame
- *
- * Purpose:	Construct an S frame.
- *
- * Input:	addrs		- Array of addresses.
- *
- *		num_addr	- Number of addresses, range 2 .. 10.
- *
- *		cr		- cr_cmd command frame, cr_res for a response frame.
- *
- *		ftype		- One of:
- *				        frame_type_S_RR,        // Receive Ready - System Ready To Receive
- *				        frame_type_S_RNR,       // Receive Not Ready - TNC Buffer Full
- *				        frame_type_S_REJ,       // Reject Frame - Out of Sequence or Duplicate
- *				        frame_type_S_SREJ,      // Selective Reject - Request single frame repeat
- *
- *		modulo		- 8 or 128.  Determines if we have 1 or 2 control bytes.
- *
- *		nr		- N(R) field --- describe.
- *
- *		pf		- Poll/Final flag.
- *
- *		pinfo		- Pointer to data for Info field.  Allowed only for SREJ.
- *
- *		info_len	- Length for Info field.
- *
- *
- * Returns:	Pointer to new packet object.
- *
- *------------------------------------------------------------------------------*/
-
-
-packet_t ax25_s_frame(char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, ax25_frame_type_t ftype, int modulo, int nr, int pf, unsigned char *pinfo, int info_len)
-{
-	packet_t this_p;
-	unsigned char *p;
-	int ctrl = 0;
-
-	this_p = ax25_new();
-
-	if (this_p == NULL) return (NULL);
-
-	if (!set_addrs(this_p, addrs, num_addr, cr)) {
-		Debugprintf("Internal error in %s: Could not set addresses for S frame.\n", __func__);
-		ax25_delete(this_p);
-		return (NULL);
-	}
-
-	if (modulo != 8 && modulo != 128) {
-		Debugprintf("Internal error in %s: Invalid modulo %d for S frame.\n", __func__, modulo);
-		modulo = 8;
-	}
-	this_p->modulo = modulo;
-
-	if (nr < 0 || nr >= modulo) {
-		Debugprintf("Internal error in %s: Invalid N(R) %d for S frame.\n", __func__, nr);
-		nr &= (modulo - 1);
-	}
-
-	// Erratum: The AX.25 spec is not clear about whether SREJ should be command, response, or both.
-	// The underlying X.25 spec clearly says it is response only.  Let's go with that.
-
-	if (ftype == frame_type_S_SREJ && cr != cr_res) {
-		Debugprintf("Internal error in %s: SREJ must be response.\n", __func__);
-	}
-
-	switch (ftype) {
-
-	case frame_type_S_RR:		ctrl = 0x01;	break;
-	case frame_type_S_RNR:	ctrl = 0x05;	break;
-	case frame_type_S_REJ:	ctrl = 0x09;	break;
-	case frame_type_S_SREJ:	ctrl = 0x0d;	break;
-
-	default:
-		Debugprintf("Internal error in %s: Invalid ftype %d for S frame.\n", __func__, ftype);
-		ax25_delete(this_p);
-		return (NULL);
-		break;
-	}
-
-	p = this_p->frame_data + this_p->frame_len;
-
-	if (modulo == 8) {
-		if (pf) ctrl |= 0x10;
-		ctrl |= nr << 5;
-		*p++ = ctrl;
-		this_p->frame_len++;
-	}
-	else {
-		*p++ = ctrl;
-		this_p->frame_len++;
-
-		ctrl = pf & 1;
-		ctrl |= nr << 1;
-		*p++ = ctrl;
-		this_p->frame_len++;
-	}
-
-	if (ftype == frame_type_S_SREJ) {
-		if (pinfo != NULL && info_len > 0) {
-			if (info_len > AX25_MAX_INFO_LEN) {
-				Debugprintf("Internal error in %s: SREJ frame, Invalid information field length %d.\n", __func__, info_len);
-				info_len = AX25_MAX_INFO_LEN;
-			}
-			memcpy(p, pinfo, info_len);
-			p += info_len;
-			this_p->frame_len += info_len;
-		}
-	}
-	else {
-		if (pinfo != NULL || info_len != 0) {
-			Debugprintf("Internal error in %s: Info part not allowed for RR, RNR, REJ frame.\n", __func__);
-		}
-	}
-	*p = '\0';
-
-
-	return (this_p);
-
-} /* end ax25_s_frame */
-
-
-
-
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_i_frame
- *
- * Purpose:	Construct an I frame.
- *
- * Input:	addrs		- Array of addresses.
- *
- *		num_addr	- Number of addresses, range 2 .. 10.
- *
- *		cr		- cr_cmd command frame, cr_res for a response frame.
- *
- *		modulo		- 8 or 128.
- *
- *		nr		- N(R) field --- describe.
- *
- *		ns		- N(S) field --- describe.
- *
- *		pf		- Poll/Final flag.
- *
- *		pid		- Protocol ID.
- *				  Normally 0xf0 meaning no level 3.
- *				  Could be other values for NET/ROM, etc.
- *
- *		pinfo		- Pointer to data for Info field.
- *
- *		info_len	- Length for Info field.
- *
- *
- * Returns:	Pointer to new packet object.
- *
- *------------------------------------------------------------------------------*/
-
-packet_t ax25_i_frame(char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, int modulo, int nr, int ns, int pf, int pid, unsigned char *pinfo, int info_len)
-{
-	packet_t this_p;
-	unsigned char *p;
-	int ctrl = 0;
-
-	this_p = ax25_new();
-
-	if (this_p == NULL) return (NULL);
-
-	if (!set_addrs(this_p, addrs, num_addr, cr)) {
-		Debugprintf("Internal error in %s: Could not set addresses for I frame.\n", __func__);
-		ax25_delete(this_p);
-		return (NULL);
-	}
-
-	if (modulo != 8 && modulo != 128) {
-		Debugprintf("Internal error in %s: Invalid modulo %d for I frame.\n", __func__, modulo);
-		modulo = 8;
-	}
-	this_p->modulo = modulo;
-
-	if (nr < 0 || nr >= modulo) {
-		Debugprintf("Internal error in %s: Invalid N(R) %d for I frame.\n", __func__, nr);
-		nr &= (modulo - 1);
-	}
-
-	if (ns < 0 || ns >= modulo) {
-		Debugprintf("Internal error in %s: Invalid N(S) %d for I frame.\n", __func__, ns);
-		ns &= (modulo - 1);
-	}
-
-	p = this_p->frame_data + this_p->frame_len;
-
-	if (modulo == 8) {
-		ctrl = (nr << 5) | (ns << 1);
-		if (pf) ctrl |= 0x10;
-		*p++ = ctrl;
-		this_p->frame_len++;
-	}
-	else {
-		ctrl = ns << 1;
-		*p++ = ctrl;
-		this_p->frame_len++;
-
-		ctrl = nr << 1;
-		if (pf) ctrl |= 0x01;
-		*p++ = ctrl;
-		this_p->frame_len++;
-	}
-
-	// Definitely don't want pid value of 0 (not in valid list)
-	// or 0xff (which means more bytes follow).
-
-	if (pid < 0 || pid == 0 || pid == 0xff) {
-		Debugprintf("Warning: Client application provided invalid PID value, 0x%02x, for I frame.\n", pid);
-		pid = AX25_PID_NO_LAYER_3;
-	}
-	*p++ = pid;
-	this_p->frame_len++;
-
-	if (pinfo != NULL && info_len > 0) {
-		if (info_len > AX25_MAX_INFO_LEN) {
-			Debugprintf("Internal error in %s: I frame, Invalid information field length %d.\n", __func__, info_len);
-			info_len = AX25_MAX_INFO_LEN;
-		}
-		memcpy(p, pinfo, info_len);
-		p += info_len;
-		this_p->frame_len += info_len;
-	}
-
-	*p = '\0';
-
-
-	return (this_p);
-
-} /* end ax25_i_frame */
-
-
-
-
-
-extern TStringList detect_list[5];
-extern TStringList detect_list_c[5];
-
-void multi_modem_process_rec_packet(int snd_ch, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, int is_fx25, int emph, int centreFreq)
-{
-	// Convert to QtSM internal format
-
-	struct TDetector_t * pDET = &DET[emph][subchan];
-	string *  data = newString();
-	char Mode[16] = "IL2P";
-
-	sprintf(Mode, "IL2P %d", centreFreq);
-
-	stringAdd(data, pp->frame_data, pp->frame_len + 2);  // QTSM assumes a CRC
-
-	ax25_delete(pp);
-
-	if (retries)
-	{
-		pDET->rx_decoded = decodedFEC;
-		pDET->emph_decoded = decodedFEC;
-		pDET->errors = retries;
-	}
-	else
-	{
-		pDET->rx_decoded = decodedNormal;
-		pDET->emph_decoded = decodedNormal;
-		pDET->errors = 0;
-	}
-
-	if (detect_list[snd_ch].Count > 0 &&
-		my_indexof(&detect_list[snd_ch], data) >= 0)
-	{
-		// Already have a copy of this frame
-
-		freeString(data);
-		Debugprintf("Discarding copy rcvr %d emph %d", subchan, 0);
-		return;
-	}
-
-	string * xx = newString();
-	memset(xx->Data, 0, 16);
-
-	Add(&detect_list_c[snd_ch], xx);
-	Add(&detect_list[snd_ch], data);
-
-//	if (retries)
-//		sprintf(Mode, "IP2P-%d", retries);
-
-	stringAdd(xx, Mode, strlen(Mode));
-	return;
-
-}
-
-
-
-
-alevel_t demod_get_audio_level(int chan, int subchan)
-{
-	alevel_t alevel;
-	alevel.rec = 0;
-	alevel.mark = 0;
-	alevel.space = 0;
-	return (alevel);
-}
-
-void ax25_hex_dump(packet_t this_p)
-{}
-
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_from_frame
- *
- * Purpose:	Split apart an HDLC frame to components.
- *
- * Inputs:	fbuf	- Pointer to beginning of frame.
- *
- *		flen	- Length excluding the two FCS bytes.
- *
- *		alevel	- Audio level of received signal.
- *			  Maximum range 0 - 100.
- *			  -1 might be used when not applicable.
- *
- * Returns:	Pointer to new packet object or NULL if error.
- *
- * Outputs:	Use the "get" functions to retrieve information in different ways.
- *
- *------------------------------------------------------------------------------*/
-
-
-packet_t ax25_from_frame(unsigned char *fbuf, int flen, alevel_t alevel)
-{
-	packet_t this_p;
-
-
-	/*
-	 * First make sure we have an acceptable length:
-	 *
-	 *	We are not concerned with the FCS (CRC) because someone else checked it.
-	 *
-	 * Is is possible to have zero length for info?
-	 *
-	 * In the original version, assuming APRS, the answer was no.
-	 * We always had at least 3 octets after the address part:
-	 * control, protocol, and first byte of info part for data type.
-	 *
-	 * In later versions, this restriction was relaxed so other
-	 * variations of AX.25 could be used.  Now the minimum length
-	 * is 7+7 for addresses plus 1 for control.
-	 *
-	 */
-
-
-	if (flen < AX25_MIN_PACKET_LEN || flen > AX25_MAX_PACKET_LEN)
-	{
-		Debugprintf("Frame length %d not in allowable range of %d to %d.", flen, AX25_MIN_PACKET_LEN, AX25_MAX_PACKET_LEN);
-		return (NULL);
-	}
-
-	this_p = ax25_new();
-
-	/* Copy the whole thing intact. */
-
-	memcpy(this_p->frame_data, fbuf, flen);
-	this_p->frame_data[flen] = 0;
-	this_p->frame_len = flen;
-
-	/* Find number of addresses. */
-
-	this_p->num_addr = (-1);
-	(void)ax25_get_num_addr(this_p);
-
-	return (this_p);
-}
-
-
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_get_num_addr
- *
- * Purpose:	Return number of addresses in current packet.
- *
- * Assumption:	ax25_from_text or ax25_from_frame was called first.
- *
- * Returns:	Number of addresses in the current packet.
- *		Should be in the range of 2 .. AX25_MAX_ADDRS.
- *
- * Version 0.9:	Could be zero for a non AX.25 frame in KISS mode.
- *
- *------------------------------------------------------------------------------*/
-
-int ax25_get_num_addr(packet_t this_p)
-{
-	//unsigned char *pf;
-	int a;
-	int addr_bytes;
-
-
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-	/* Use cached value if already set. */
-
-	if (this_p->num_addr >= 0) {
-		return (this_p->num_addr);
-	}
-
-	/* Otherwise, determine the number ofaddresses. */
-
-	this_p->num_addr = 0;		/* Number of addresses extracted. */
-
-	addr_bytes = 0;
-	for (a = 0; a < this_p->frame_len && addr_bytes == 0; a++) {
-		if (this_p->frame_data[a] & SSID_LAST_MASK) {
-			addr_bytes = a + 1;
-		}
-	}
-
-	if (addr_bytes % 7 == 0) {
-		int addrs = addr_bytes / 7;
-		if (addrs >= AX25_MIN_ADDRS && addrs <= AX25_MAX_ADDRS) {
-			this_p->num_addr = addrs;
-		}
-	}
-
-	return (this_p->num_addr);
-}
-
-
-
-void ax25_get_addr_with_ssid(packet_t pp, int n, char *station)
-{}
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_get_addr_no_ssid
- *
- * Purpose:	Return specified address WITHOUT any SSID.
- *
- * Inputs:	n	- Index of address.   Use the symbols
- *			  AX25_DESTINATION, AX25_SOURCE, AX25_REPEATER1, etc.
- *
- * Outputs:	station - String representation of the station, WITHOUT the SSID.
- *			e.g.  "WB2OSZ"
- *			  Usually variables will be AX25_MAX_ADDR_LEN bytes
- *			  but 7 would be adequate.
- *
- * Bugs:	No bounds checking is performed.  Be careful.
- *
- * Assumption:	ax25_from_text or ax25_from_frame was called first.
- *
- * Returns:	Character string in usual human readable format,
- *
- *
- *------------------------------------------------------------------------------*/
-
-void ax25_get_addr_no_ssid(packet_t this_p, int n, char *station)
-{
-	int i;
-
-	//assert(this_p->magic1 == MAGIC);
-	//assert(this_p->magic2 == MAGIC);
-
-
-	if (n < 0) {
-		Debugprintf("Internal error detected in ax25_get_addr_no_ssid, %s, line %d.\n", __FILE__, __LINE__);
-		Debugprintf("Address index, %d, is less than zero.\n", n);
-		strcpy(station, "??????");
-		return;
-	}
-
-	if (n >= this_p->num_addr) {
-		Debugprintf("Internal error detected in ax25_get_no_with_ssid, %s, line %d.\n", __FILE__, __LINE__);
-		Debugprintf("Address index, %d, is too large for number of addresses, %d.\n", n, this_p->num_addr);
-		strcpy(station, "??????");
-		return;
-	}
-
-	// At one time this would stop at the first space, on the assumption we would have only trailing spaces.
-	// Then there was a forum discussion where someone encountered the address " WIDE2" with a leading space.
-	// In that case, we would have returned a zero length string here.
-	// Now we return exactly what is in the address field and trim trailing spaces.
-	// This will provide better information for troubleshooting.
-
-	for (i = 0; i < 6; i++) {
-		station[i] = (this_p->frame_data[n * 7 + i] >> 1) & 0x7f;
-	}
-	station[6] = '\0';
-
-	for (i = 5; i >= 0; i--) {
-		if (station[i] == ' ')
-			station[i] = '\0';
-		else
-			break;
-	}
-
-	if (strlen(station) == 0) {
-		Debugprintf("Station address, in position %d, is empty!  This is not a valid AX.25 frame.\n", n);
-	}
-
-} /* end ax25_get_addr_no_ssid */
-
-
-/*------------------------------------------------------------------------------
- *
- * Name:	ax25_get_ssid
- *
- * Purpose:	Return SSID of specified address in current packet.
- *
- * Inputs:	n	- Index of address.   Use the symbols
- *			  AX25_DESTINATION, AX25_SOURCE, AX25_REPEATER1, etc.
- *
- * Assumption:	ax25_from_text or ax25_from_frame was called first.
- *
- * Returns:	Substation id, as integer 0 .. 15.
- *
- *------------------------------------------------------------------------------*/
-
-int ax25_get_ssid(packet_t this_p, int n)
-{
-
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-	if (n >= 0 && n < this_p->num_addr) {
-		return ((this_p->frame_data[n * 7 + 6] & SSID_SSID_MASK) >> SSID_SSID_SHIFT);
-	}
-	else {
-		Debugprintf("Internal error: ax25_get_ssid(%d), num_addr=%d\n", n, this_p->num_addr);
-		return (0);
-	}
-}
-
-
-
-static inline int ax25_get_pid_offset(packet_t this_p)
-{
-	return (ax25_get_control_offset(this_p) + ax25_get_num_control(this_p));
-}
-
-static int ax25_get_num_pid(packet_t this_p)
-{
-	int c;
-	int pid;
-
-	c = this_p->frame_data[ax25_get_control_offset(this_p)];
-
-	if ((c & 0x01) == 0 ||				/* I   xxxx xxx0 */
-		c == 0x03 || c == 0x13) {			/* UI  000x 0011 */
-
-		pid = this_p->frame_data[ax25_get_pid_offset(this_p)];
-		if (pid == AX25_PID_ESCAPE_CHARACTER) {
-			return (2);			/* pid 1111 1111 means another follows. */
-		}
-		return (1);
-	}
-	return (0);
-}
-
-
-inline int ax25_get_control_offset(packet_t this_p)
-{
-	return (this_p->num_addr * 7);
-}
-
-inline int ax25_get_num_control(packet_t this_p)
-{
-	int c;
-
-	c = this_p->frame_data[ax25_get_control_offset(this_p)];
-
-	if ((c & 0x01) == 0) {			/* I   xxxx xxx0 */
-		return ((this_p->modulo == 128) ? 2 : 1);
-	}
-
-	if ((c & 0x03) == 1) {			/* S   xxxx xx01 */
-		return ((this_p->modulo == 128) ? 2 : 1);
-	}
-
-	return (1);					/* U   xxxx xx11 */
-}
-
-
-
-
-int ax25_get_info_offset(packet_t this_p)
-{
-	int offset = ax25_get_control_offset(this_p) + ax25_get_num_control(this_p) + ax25_get_num_pid(this_p);
-	return (offset);
-}
-
-int ax25_get_num_info(packet_t this_p)
-{
-	int len;
-
-	/* assuming AX.25 frame. */
-
-	len = this_p->frame_len - this_p->num_addr * 7 - ax25_get_num_control(this_p) - ax25_get_num_pid(this_p);
-	if (len < 0) {
-		len = 0;		/* print error? */
-	}
-
-	return (len);
-}
-
-
-
-
-
-	/*------------------------------------------------------------------------------
-	 *
-	 * Name:	ax25_get_info
-	 *
-	 * Purpose:	Obtain Information part of current packet.
-	 *
-	 * Inputs:	this_p	- Packet object pointer.
-	 *
-	 * Outputs:	paddr	- Starting address of information part is returned here.
-	 *
-	 * Assumption:	ax25_from_text or ax25_from_frame was called first.
-	 *
-	 * Returns:	Number of octets in the Information part.
-	 *		Should be in the range of AX25_MIN_INFO_LEN .. AX25_MAX_INFO_LEN.
-	 *
-	 *------------------------------------------------------------------------------*/
-
-int ax25_get_info(packet_t this_p, unsigned char **paddr)
-{
-	unsigned char *info_ptr;
-	int info_len;
-
-
-	//assert(this_p->magic1 == MAGIC);
-	//assert(this_p->magic2 == MAGIC);
-
-	if (this_p->num_addr >= 2) {
-
-		/* AX.25 */
-
-		info_ptr = this_p->frame_data + ax25_get_info_offset(this_p);
-		info_len = ax25_get_num_info(this_p);
-	}
-	else {
-
-		/* Not AX.25.  Treat Whole packet as info. */
-
-		info_ptr = this_p->frame_data;
-		info_len = this_p->frame_len;
-	}
-
-	/* Add nul character in case caller treats as printable string. */
-
-//		assert(info_len >= 0);
-
-	info_ptr[info_len] = '\0';
-
-	*paddr = info_ptr;
-	return (info_len);
-
-} /* end ax25_get_info */
-
-
-
-
-void ax25_set_info(packet_t this_p, unsigned char *new_info_ptr, int new_info_len)
-{
-	unsigned char *old_info_ptr;
-	int old_info_len = ax25_get_info(this_p, &old_info_ptr);
-	this_p->frame_len -= old_info_len;
-
-	if (new_info_len < 0) new_info_len = 0;
-	if (new_info_len > AX25_MAX_INFO_LEN) new_info_len = AX25_MAX_INFO_LEN;
-	memcpy(old_info_ptr, new_info_ptr, new_info_len);
-	this_p->frame_len += new_info_len;
-}
-
-int ax25_get_pid(packet_t this_p)
-{
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-	// TODO: handle 2 control byte case.
-	// TODO: sanity check: is it I or UI frame?
-
-	if (this_p->frame_len == 0) return(-1);
-
-	if (this_p->num_addr >= 2) {
-		return (this_p->frame_data[ax25_get_pid_offset(this_p)]);
-	}
-	return (-1);
-}
-
-
-int ax25_get_frame_len(packet_t this_p)
-{
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-//	assert(this_p->frame_len >= 0 && this_p->frame_len <= AX25_MAX_PACKET_LEN);
-
-	return (this_p->frame_len);
-
-} /* end ax25_get_frame_len */
-
-
-unsigned char *ax25_get_frame_data_ptr(packet_t this_p)
-{
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-	return (this_p->frame_data);
-
-} /* end ax25_get_frame_data_ptr */
-
-
-int ax25_get_modulo(packet_t this_p)
-{
-	return 7;
-}
-
-
-/*------------------------------------------------------------------
- *
- * Function:	ax25_get_control
-		ax25_get_c2
- *
- * Purpose:	Get Control field from packet.
- *
- * Inputs:	this_p	- pointer to packet object.
- *
- * Returns:	APRS uses AX25_UI_FRAME.
- *		This could also be used in other situations.
- *
- *------------------------------------------------------------------*/
-
-
-int ax25_get_control(packet_t this_p)
-{
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-	if (this_p->frame_len == 0) return(-1);
-
-	if (this_p->num_addr >= 2) {
-		return (this_p->frame_data[ax25_get_control_offset(this_p)]);
-	}
-	return (-1);
-}
-
-
-/*------------------------------------------------------------------
-*
-* Function:	ax25_frame_type
-*
-* Purpose : Extract the type of frame.
-*		This is derived from the control byte(s) but
-*		is an enumerated type for easier handling.
-*
-* Inputs : this_p - pointer to packet object.
-*
-* Outputs : desc - Text description such as "I frame" or
-*"U frame SABME".
-*			  Supply 56 bytes to be safe.
-*
-*		cr - Command or response ?
-*
-*		pf - P / F - Poll / Final or -1 if not applicable
-*
-*		nr - N(R) - receive sequence or -1 if not applicable.
-*
-*		ns - N(S) - send sequence or -1 if not applicable.
-*
-* Returns:	Frame type from  enum ax25_frame_type_e.
-*
-*------------------------------------------------------------------*/
-
-// TODO: need someway to ensure caller allocated enough space.
-// Should pass in as parameter.
-
-#define DESC_SIZ 56
-
-
-ax25_frame_type_t ax25_frame_type(packet_t this_p, cmdres_t *cr, char *desc, int *pf, int *nr, int *ns)
-{
-	int c;		// U frames are always one control byte.
-	int c2 = 0;	// I & S frames can have second Control byte.
-
-//	assert(this_p->magic1 == MAGIC);
-//	assert(this_p->magic2 == MAGIC);
-
-
-	strcpy(desc, "????");
-	*cr = cr_11;
-	*pf = -1;
-	*nr = -1;
-	*ns = -1;
-
-	c = ax25_get_control(this_p);
-	if (c < 0) {
-		strcpy(desc, "Not AX.25");
-		return (frame_not_AX25);
-	}
-
-	/*
-	 * TERRIBLE HACK :-(  for display purposes.
-	 *
-	 * I and S frames can have 1 or 2 control bytes but there is
-	 * no good way to determine this without dipping into the data
-	 * link state machine.  Can we guess?
-	 *
-	 * S frames have no protocol id or information so if there is one
-	 * more byte beyond the control field, we could assume there are
-	 * two control bytes.
-	 *
-	 * For I frames, the protocol id will usually be 0xf0.  If we find
-	 * that as the first byte of the information field, it is probably
-	 * the pid and not part of the information.  Ditto for segments 0x08.
-	 * Not fool proof but good enough for troubleshooting text out.
-	 *
-	 * If we have a link to the peer station, this will be set properly
-	 * before it needs to be used for other reasons.
-	 *
-	 * Setting one of the RR bits (find reference!) is sounding better and better.
-	 * It's in common usage so I should lobby to get that in the official protocol spec.
-	 */
-
-	// Dont support mod 128
-/*
-	if (this_p->modulo == 0 && (c & 3) == 1 && ax25_get_c2(this_p) != -1) {
-		this_p->modulo = modulo_128;
-	}
-	else if (this_p->modulo == 0 && (c & 1) == 0 && this_p->frame_data[ax25_get_info_offset(this_p)] == 0xF0) {
-		this_p->modulo = modulo_128;
-	}
-	else if (this_p->modulo == 0 && (c & 1) == 0 && this_p->frame_data[ax25_get_info_offset(this_p)] == 0x08) {	// same for segments
-		this_p->modulo = modulo_128;
-	}
-
-
-	if (this_p->modulo == modulo_128) {
-		c2 = ax25_get_c2(this_p);
-	}
-*/
-
-		int dst_c = this_p->frame_data[AX25_DESTINATION * 7 + 6] & SSID_H_MASK;
-		int src_c = this_p->frame_data[AX25_SOURCE * 7 + 6] & SSID_H_MASK;
-
-		char cr_text[8];
-		char pf_text[8];
-
-		if (dst_c) {
-			if (src_c) { *cr = cr_11;  strcpy(cr_text, "cc=11"); strcpy(pf_text, "p/f"); }
-			else { *cr = cr_cmd; strcpy(cr_text, "cmd");   strcpy(pf_text, "p"); }
-		}
-		else {
-			if (src_c) { *cr = cr_res; strcpy(cr_text, "res");   strcpy(pf_text, "f"); }
-			else { *cr = cr_00;  strcpy(cr_text, "cc=00"); strcpy(pf_text, "p/f"); }
-		}
-
-		if ((c & 1) == 0) {
-
-			// Information 			rrr p sss 0		or	sssssss 0  rrrrrrr p
-
-			if (this_p->modulo == modulo_128) {
-				*ns = (c >> 1) & 0x7f;
-				*pf = c2 & 1;
-				*nr = (c2 >> 1) & 0x7f;
-			}
-			else {
-				*ns = (c >> 1) & 7;
-				*pf = (c >> 4) & 1;
-				*nr = (c >> 5) & 7;
-			}
-
-			//snprintf (desc, DESC_SIZ, "I %s, n(s)=%d, n(r)=%d, %s=%d", cr_text, *ns, *nr, pf_text, *pf);
-			sprintf(desc, "I %s, n(s)=%d, n(r)=%d, %s=%d, pid=0x%02x", cr_text, *ns, *nr, pf_text, *pf, ax25_get_pid(this_p));
-			return (frame_type_I);
-		}
-		else if ((c & 2) == 0) {
-
-			// Supervisory			rrr p/f ss 0 1		or	0000 ss 0 1  rrrrrrr p/f
-
-			if (this_p->modulo == modulo_128) {
-				*pf = c2 & 1;
-				*nr = (c2 >> 1) & 0x7f;
-			}
-			else {
-				*pf = (c >> 4) & 1;
-				*nr = (c >> 5) & 7;
-			}
-
-
-			switch ((c >> 2) & 3) {
-			case 0: sprintf(desc, "RR %s, n(r)=%d, %s=%d", cr_text, *nr, pf_text, *pf);   return (frame_type_S_RR);   break;
-			case 1: sprintf(desc, "RNR %s, n(r)=%d, %s=%d", cr_text, *nr, pf_text, *pf);  return (frame_type_S_RNR);  break;
-			case 2: sprintf(desc, "REJ %s, n(r)=%d, %s=%d", cr_text, *nr, pf_text, *pf);  return (frame_type_S_REJ);  break;
-			case 3: sprintf(desc, "SREJ %s, n(r)=%d, %s=%d", cr_text, *nr, pf_text, *pf); return (frame_type_S_SREJ); break;
-			}
-		}
-		else {
-
-			// Unnumbered			mmm p/f mm 1 1
-
-			*pf = (c >> 4) & 1;
-
-			switch (c & 0xef) {
-
-			case 0x6f: sprintf(desc, "SABME %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_SABME); break;
-			case 0x2f: sprintf(desc, "SABM %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_SABM);  break;
-			case 0x43: sprintf(desc, "DISC %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_DISC);  break;
-			case 0x0f: sprintf(desc, "DM %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_DM);    break;
-			case 0x63: sprintf(desc, "UA %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_UA);    break;
-			case 0x87: sprintf(desc, "FRMR %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_FRMR);  break;
-			case 0x03: sprintf(desc, "UI %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_UI);    break;
-			case 0xaf: sprintf(desc, "XID %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_XID);   break;
-			case 0xe3: sprintf(desc, "TEST %s, %s=%d", cr_text, pf_text, *pf);  return (frame_type_U_TEST);  break;
-			default:   sprintf(desc, "U other???");        				 return (frame_type_U);       break;
-			}
-		}
-
-		// Should be unreachable but compiler doesn't realize that.
-		// Here only to suppress "warning: control reaches end of non-void function"
-
-	return (frame_not_AX25);
-
-} /* end ax25_frame_type */
-
-
-
-packet_t ax25_u_frame(char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr, ax25_frame_type_t ftype, int pf, int pid, unsigned char *pinfo, int info_len)
-{
-	packet_t this_p;
-	unsigned char *p;
-	int ctrl = 0;
-	unsigned int t = 999;	// 1 = must be cmd, 0 = must be response, 2 = can be either.
-	int i = 0;		// Is Info part allowed?
-
-	this_p = ax25_new();
-
-	if (this_p == NULL) return (NULL);
-
-	this_p->modulo = 0;
-
-	if (!set_addrs(this_p, addrs, num_addr, cr)) {
-		Debugprintf("Internal error in %s: Could not set addresses for U frame.\n", __func__);
-		ax25_delete(this_p);
-		return (NULL);
-	}
-
-	switch (ftype) {
-		// 1 = cmd only, 0 = res only, 2 = either
-	case frame_type_U_SABME:	ctrl = 0x6f;	t = 1;		break;
-	case frame_type_U_SABM:	ctrl = 0x2f;	t = 1;		break;
-	case frame_type_U_DISC:	ctrl = 0x43;	t = 1;		break;
-	case frame_type_U_DM:		ctrl = 0x0f;	t = 0;		break;
-	case frame_type_U_UA:		ctrl = 0x63;	t = 0;		break;
-	case frame_type_U_FRMR:	ctrl = 0x87;	t = 0;	i = 1;	break;
-	case frame_type_U_UI:		ctrl = 0x03;	t = 2;	i = 1;	break;
-	case frame_type_U_XID:	ctrl = 0xaf;	t = 2;	i = 1;	break;
-	case frame_type_U_TEST:	ctrl = 0xe3;	t = 2;	i = 1;	break;
-
-	default:
-		Debugprintf("Internal error in %s: Invalid ftype %d for U frame.\n", __func__, ftype);
-		ax25_delete(this_p);
-		return (NULL);
-		break;
-	}
-	if (pf) ctrl |= 0x10;
-
-	if (t != 2) {
-		if (cr != t) {
-			Debugprintf("Internal error in %s: U frame, cr is %d but must be %d. ftype=%d\n", __func__, cr, t, ftype);
-		}
-	}
-
-	p = this_p->frame_data + this_p->frame_len;
-	*p++ = ctrl;
-	this_p->frame_len++;
-
-	if (ftype == frame_type_U_UI) {
-
-		// Definitely don't want pid value of 0 (not in valid list)
-		// or 0xff (which means more bytes follow).
-
-		if (pid < 0 || pid == 0 || pid == 0xff) {
-			Debugprintf("Internal error in %s: U frame, Invalid pid value 0x%02x.\n", __func__, pid);
-			pid = AX25_PID_NO_LAYER_3;
-		}
-		*p++ = pid;
-		this_p->frame_len++;
-	}
-
-	if (i) {
-		if (pinfo != NULL && info_len > 0) {
-			if (info_len > AX25_MAX_INFO_LEN) {
-
-				Debugprintf("Internal error in %s: U frame, Invalid information field length %d.\n", __func__, info_len);
-				info_len = AX25_MAX_INFO_LEN;
-			}
-			memcpy(p, pinfo, info_len);
-			p += info_len;
-			this_p->frame_len += info_len;
-		}
-	}
-	else {
-		if (pinfo != NULL && info_len > 0) {
-			Debugprintf("Internal error in %s: Info part not allowed for U frame type.\n", __func__);
-		}
-	}
-	*p = '\0';
-
-	//assert(p == this_p->frame_data + this_p->frame_len);
-	//assert(this_p->magic1 == MAGIC);
-	//assert(this_p->magic2 == MAGIC);
-
-#if PAD2TEST
-	ax25_frame_type_t check_ftype;
-	cmdres_t check_cr;
-	char check_desc[80];
-	int check_pf;
-	int check_nr;
-	int check_ns;
-
-	check_ftype = ax25_frame_type(this_p, &check_cr, check_desc, &check_pf, &check_nr, &check_ns);
-
-	text_color_set(DW_COLOR_DEBUG);
-	Debugprintf("check: ftype=%d, desc=\"%s\", pf=%d\n", check_ftype, check_desc, check_pf);
-
-	assert(check_cr == cr);
-	assert(check_ftype == ftype);
-	assert(check_pf == pf);
-	assert(check_nr == -1);
-	assert(check_ns == -1);
-
-#endif
-
-	return (this_p);
-
-} /* end ax25_u_frame */
-
-
-
-
-
-
-static const char *position_name[1 + AX25_MAX_ADDRS] = {
-	"", "Destination ", "Source ",
-	"Digi1 ", "Digi2 ", "Digi3 ", "Digi4 ",
-	"Digi5 ", "Digi6 ", "Digi7 ", "Digi8 " };
-
-int ax25_parse_addr(int position, char *in_addr, int strict, char *out_addr, int *out_ssid, int *out_heard)
-{
-	char *p;
-	char sstr[8];		/* Should be 1 or 2 digits for SSID. */
-	int i, j, k;
-	int maxlen;
-
-	*out_addr = '\0';
-	*out_ssid = 0;
-	*out_heard = 0;
-
-	// Debugprintf ("ax25_parse_addr in: position=%d, '%s', strict=%d\n", position, in_addr, strict);
-
-	if (position < -1) position = -1;
-	if (position > AX25_REPEATER_8) position = AX25_REPEATER_8;
-	position++;	/* Adjust for position_name above. */
-
-	if (strlen(in_addr) == 0) {
-		Debugprintf("%sAddress \"%s\" is empty.\n", position_name[position], in_addr);
-		return 0;
-	}
-
-	if (strict && strlen(in_addr) >= 2 && strncmp(in_addr, "qA", 2) == 0) {
-
-		Debugprintf("%sAddress \"%s\" is a \"q-construct\" used for communicating with\n", position_name[position], in_addr);
-		Debugprintf("APRS Internet Servers.  It should never appear when going over the radio.\n");
-	}
-
-	// Debugprintf ("ax25_parse_addr in: %s\n", in_addr);
-
-	maxlen = strict ? 6 : (AX25_MAX_ADDR_LEN - 1);
-	p = in_addr;
-	i = 0;
-	for (p = in_addr; *p != '\0' && *p != '-' && *p != '*'; p++) {
-		if (i >= maxlen) {
-			Debugprintf("%sAddress is too long. \"%s\" has more than %d characters.\n", position_name[position], in_addr, maxlen);
-			return 0;
-		}
-		if (!isalnum(*p)) {
-			Debugprintf("%sAddress, \"%s\" contains character other than letter or digit in character position %d.\n", position_name[position], in_addr, (int)(long)(p - in_addr) + 1);
-			return 0;
-		}
-
-		out_addr[i++] = *p;
-		out_addr[i] = '\0';
-
-#if DECAMAIN	// Hack when running in decode_aprs utility.
-		// Exempt the "qA..." case because it was already mentioned.
-
-		if (strict && islower(*p) && strncmp(in_addr, "qA", 2) != 0) {
-			text_color_set(DW_COLOR_ERROR);
-			Debugprintf("%sAddress has lower case letters. \"%s\" must be all upper case.\n", position_name[position], in_addr);
-		}
-#else
-		if (strict && islower(*p)) {
-			Debugprintf("%sAddress has lower case letters. \"%s\" must be all upper case.\n", position_name[position], in_addr);
-			return 0;
-		}
-#endif
-	}
-
-	j = 0;
-	sstr[j] = '\0';
-	if (*p == '-') {
-		for (p++; isalnum(*p); p++) {
-			if (j >= 2) {
-				Debugprintf("%sSSID is too long. SSID part of \"%s\" has more than 2 characters.\n", position_name[position], in_addr);
-				return 0;
-			}
-			sstr[j++] = *p;
-			sstr[j] = '\0';
-			if (strict && !isdigit(*p)) {
-				Debugprintf("%sSSID must be digits. \"%s\" has letters in SSID.\n", position_name[position], in_addr);
-				return 0;
-			}
-		}
-		k = atoi(sstr);
-		if (k < 0 || k > 15) {
-			Debugprintf("%sSSID out of range. SSID of \"%s\" not in range of 0 to 15.\n", position_name[position], in_addr);
-			return 0;
-		}
-		*out_ssid = k;
-	}
-
-	if (*p == '*') {
-		*out_heard = 1;
-		p++;
-		if (strict == 2) {
-			Debugprintf("\"*\" is not allowed at end of address \"%s\" here.\n", in_addr);
-			return 0;
-		}
-	}
-
-	if (*p != '\0') {
-		Debugprintf("Invalid character \"%c\" found in %saddress \"%s\".\n", *p, position_name[position], in_addr);
-		return 0;
-	}
-
-	// Debugprintf ("ax25_parse_addr out: '%s' %d %d\n", out_addr, *out_ssid, *out_heard);
-
-	return (1);
-
-} /* end ax25_parse_addr */
-
-
-
-int set_addrs(packet_t pp, char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, cmdres_t cr)
-{
-	int n;
-
-	//assert(pp->frame_len == 0);
-	//assert(cr == cr_cmd || cr == cr_res);
-
-	if (num_addr < AX25_MIN_ADDRS || num_addr > AX25_MAX_ADDRS) {
-		Debugprintf("INTERNAL ERROR: %s %s %d, num_addr = %d\n", __FILE__, __func__, __LINE__, num_addr);
-		return (0);
-	}
-
-	for (n = 0; n < num_addr; n++) {
-
-		unsigned char *pa = pp->frame_data + n * 7;
-		int ok;
-		int strict = 1;
-		char oaddr[AX25_MAX_ADDR_LEN];
-		int ssid;
-		int heard;
-		int j;
-
-		ok = ax25_parse_addr(n, addrs[n], strict, oaddr, &ssid, &heard);
-
-		if (!ok) return (0);
-
-		// Fill in address.
-
-		memset(pa, ' ' << 1, 6);
-		for (j = 0; oaddr[j]; j++) {
-			pa[j] = oaddr[j] << 1;
-		}
-		pa += 6;
-
-		// Fill in SSID.
-
-		*pa = 0x60 | ((ssid & 0xf) << 1);
-
-		// Command / response flag.
-
-		switch (n) {
-		case AX25_DESTINATION:
-			if (cr == cr_cmd) *pa |= 0x80;
-			break;
-		case AX25_SOURCE:
-			if (cr == cr_res) *pa |= 0x80;
-			break;
-		default:
-			break;
-		}
-
-		// Is this the end of address field?
-
-		if (n == num_addr - 1) {
-			*pa |= 1;
-		}
-
-		pp->frame_len += 7;
-	}
-
-	pp->num_addr = num_addr;
-	return (1);
-
-} /* end set_addrs */
-
-
-
-///////////////////////////////////////////////////////////////////////////////
-//
-// 	il2p_init.c
-//
-///////////////////////////////////////////////////////////////////////////////
-
-
-// Init must be called at start of application.
-
-extern void il2p_init(int debug);
-
-extern struct rs *il2p_find_rs(int nparity);	// Internal later?
-
-extern void il2p_encode_rs(unsigned char *tx_data, int data_size, int num_parity, unsigned char *parity_out);
-
-extern int il2p_decode_rs(unsigned char *rec_block, int data_size, int num_parity, unsigned char *out);
-
-extern int il2p_get_debug(void);
-extern void il2p_set_debug(int debug);
-
-
-///////////////////////////////////////////////////////////////////////////////
-//
-// 	il2p_rec.c
-//
-///////////////////////////////////////////////////////////////////////////////
-
-// Receives a bit stream from demodulator.
-
-extern void il2p_rec_bit(int chan, int subchan, int slice, int dbit);
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////
-//
-// 	il2p_send.c
-//
-///////////////////////////////////////////////////////////////////////////////
-
-
-// Send bit stream to modulator.
-
-string * il2p_send_frame(int chan, packet_t pp, int max_fec, int polarity);
-
-
-
-///////////////////////////////////////////////////////////////////////////////
-//
-// 	il2p_codec.c
-//
-///////////////////////////////////////////////////////////////////////////////
-
-
-extern int il2p_encode_frame(packet_t pp, int max_fec, unsigned char *iout);
-
-packet_t il2p_decode_frame(unsigned char *irec);
-
-packet_t il2p_decode_header_payload(unsigned char* uhdr, unsigned char *epayload, int *symbols_corrected);
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////
-//
-// 	il2p_header.c
-//
-///////////////////////////////////////////////////////////////////////////////
-
-
-extern int il2p_type_1_header(packet_t pp, int max_fec, unsigned char *hdr);
-
-extern packet_t il2p_decode_header_type_1(unsigned char *hdr, int num_sym_changed);
-
-
-extern int il2p_type_0_header(packet_t pp, int max_fec, unsigned char *hdr);
-
-extern int il2p_clarify_header(unsigned char *rec_hdr, unsigned char *corrected_descrambled_hdr);
-
-
-
-///////////////////////////////////////////////////////////////////////////////
-//
-// 	il2p_scramble.c
-//
-///////////////////////////////////////////////////////////////////////////////
-
-extern void il2p_scramble_block(unsigned char *in, unsigned char *out, int len);
-
-extern void il2p_descramble_block(unsigned char *in, unsigned char *out, int len);
-
-
-///////////////////////////////////////////////////////////////////////////////
-//
-// 	il2p_payload.c
-//
-///////////////////////////////////////////////////////////////////////////////
-
-
-typedef struct {
-	int payload_byte_count;		// Total size, 0 thru 1023
-	int payload_block_count;
-	int small_block_size;
-	int large_block_size;
-	int large_block_count;
-	int small_block_count;
-	int parity_symbols_per_block;	// 2, 4, 6, 8, 16
-} il2p_payload_properties_t;
-
-extern int il2p_payload_compute(il2p_payload_properties_t *p, int payload_size, int max_fec);
-
-extern int il2p_encode_payload(unsigned char *payload, int payload_size, int max_fec, unsigned char *enc);
-
-extern int il2p_decode_payload(unsigned char *received, int payload_size, int max_fec, unsigned char *payload_out, int *symbols_corrected);
-
-extern int il2p_get_header_attributes(unsigned char *hdr, int *hdr_type, int *max_fec);
-
-#endif
-
-
-
-// Interesting related stuff:
-// https://www.kernel.org/doc/html/v4.15/core-api/librs.html
-// https://berthub.eu/articles/posts/reed-solomon-for-programmers/ 
-
-
-#define MAX_NROOTS 16
-
-#define NTAB 5
-
-static struct {
-	int symsize;          // Symbol size, bits (1-8).  Always 8 for this application.
-	int genpoly;          // Field generator polynomial coefficients.
-	int fcs;              // First root of RS code generator polynomial, index form.
-			  // FX.25 uses 1 but IL2P uses 0.
-	int prim;             // Primitive element to generate polynomial roots.
-	int nroots;           // RS code generator polynomial degree (number of roots).
-						  // Same as number of check bytes added.
-	struct rs *rs;        // Pointer to RS codec control block.  Filled in at init time.
-} Tab[NTAB] = {
-  {8, 0x11d,   0,   1, 2, NULL },  // 2 parity
-  {8, 0x11d,   0,   1, 4, NULL },  // 4 parity
-  {8, 0x11d,   0,   1, 6, NULL },  // 6 parity
-  {8, 0x11d,   0,   1, 8, NULL },  // 8 parity
-  {8, 0x11d,   0,   1, 16, NULL },  // 16 parity
-};
-
-
-
-static int g_il2p_debug = 0;
-
-
-/*-------------------------------------------------------------
- *
- * Name:	il2p_init
- *
- * Purpose:	This must be called at application start up time.
- *		It sets up tables for the Reed-Solomon functions.
- *
- * Inputs:	debug	- Enable debug output.
- *
- *--------------------------------------------------------------*/
-
-void il2p_init(int il2p_debug)
-{
-	g_il2p_debug = il2p_debug;
-
-	for (int i = 0; i < NTAB; i++) {
-		//assert(Tab[i].nroots <= MAX_NROOTS);
-		Tab[i].rs = INIT_RS(Tab[i].symsize, Tab[i].genpoly, Tab[i].fcs, Tab[i].prim, Tab[i].nroots);
-		if (Tab[i].rs == NULL) {
-			Debugprintf("IL2P internal error: init_rs_char failed!\n");
-			exit(0);
-		}
-	}
-
-} // end il2p_init
-
-
-int il2p_get_debug(void)
-{
-	return (g_il2p_debug);
-}
-void il2p_set_debug(int debug)
-{
-	g_il2p_debug = debug;
-}
-
-
-// Find RS codec control block for specified number of parity symbols.
-
-struct rs *il2p_find_rs(int nparity)
-{
-	for (int n = 0; n < NTAB; n++) {
-		if (Tab[n].nroots == nparity) {
-			return (Tab[n].rs);
-		}
-	}
-	Debugprintf("IL2P INTERNAL ERROR: il2p_find_rs: control block not found for nparity = %d.\n", nparity);
-	return (Tab[0].rs);
-}
-
-
-/*-------------------------------------------------------------
- *
- * Name:	void il2p_encode_rs
- *
- * Purpose:	Add parity symbols to a block of data.
- *
- * Inputs:	tx_data		Header or other data to transmit.
- *		data_size	Number of data bytes in above.
- *		num_parity	Number of parity symbols to add.
- *				Maximum of IL2P_MAX_PARITY_SYMBOLS.
- *
- * Outputs:	parity_out	Specified number of parity symbols
- *
- * Restriction:	data_size + num_parity <= 255 which is the RS block size.
- *		The caller must ensure this.
- *
- *--------------------------------------------------------------*/
-
-void il2p_encode_rs(unsigned char *tx_data, int data_size, int num_parity, unsigned char *parity_out)
-{
-	//assert(data_size >= 1);
-	//assert(num_parity == 2 || num_parity == 4 || num_parity == 6 || num_parity == 8 || num_parity == 16);
-	//assert(data_size + num_parity <= 255);
-
-	unsigned char rs_block[FX25_BLOCK_SIZE];
-	memset(rs_block, 0, sizeof(rs_block));
-	memcpy(rs_block + sizeof(rs_block) - data_size - num_parity, tx_data, data_size);
-	ENCODE_RS(il2p_find_rs(num_parity), rs_block, parity_out);
-}
-
-/*-------------------------------------------------------------
- *
- * Name:	void il2p_decode_rs
- *
- * Purpose:	Check and attempt to fix block with FEC.
- *
- * Inputs:	rec_block	Received block composed of data and parity.
- *				Total size is sum of following two parameters.
- *		data_size	Number of data bytes in above.
- *		num_parity	Number of parity symbols (bytes) in above.
- *
- * Outputs:	out		Original with possible corrections applied.
- *				data_size bytes.
- *
- * Returns:	-1 for unrecoverable.
- *		>= 0 for success.  Number of symbols corrected.
- *
- *--------------------------------------------------------------*/
-
-int il2p_decode_rs(unsigned char *rec_block, int data_size, int num_parity, unsigned char *out)
-{
-
-	//  Use zero padding in front if data size is too small.
-
-	int n = data_size + num_parity;		// total size in.
-
-	unsigned char rs_block[FX25_BLOCK_SIZE];
-
-	// We could probably do this more efficiently by skipping the
-	// processing of the bytes known to be zero.  Good enough for now.
-
-	memset(rs_block, 0, sizeof(rs_block) - n);
-	memcpy(rs_block + sizeof(rs_block) - n, rec_block, n);
-
-	if (il2p_get_debug() >= 3) {
-		Debugprintf("==============================  il2p_decode_rs  ==============================\n");
-		Debugprintf("%d filler zeros, %d data, %d parity\n", (int)(sizeof(rs_block) - n), data_size, num_parity);
-		fx_hex_dump(rs_block, sizeof(rs_block));
-	}
-
-	int derrlocs[FX25_MAX_CHECK];	// Half would probably be OK.
-
-	int derrors = DECODE_RS(il2p_find_rs(num_parity), rs_block, derrlocs, 0);
-	memcpy(out, rs_block + sizeof(rs_block) - n, data_size);
-
-	if (il2p_get_debug() >= 3) {
-		if (derrors == 0) {
-			Debugprintf("No errors reported for RS block.\n");
-		}
-		else if (derrors > 0) {
-			Debugprintf("%d errors fixed in positions:\n", derrors);
-			for (int j = 0; j < derrors; j++) {
-				Debugprintf("        %3d  (0x%02x)\n", derrlocs[j], derrlocs[j]);
-			}
-			fx_hex_dump(rs_block, sizeof(rs_block));
-		}
-	}
-
-	// It is possible to have a situation where too many errors are
-	// present but the algorithm could get a good code block by "fixing"
-	// one of the padding bytes that should be 0.
-
-	for (int i = 0; i < derrors; i++) {
-		if (derrlocs[i] < sizeof(rs_block) - n) {
-			if (il2p_get_debug() >= 3) {
-				Debugprintf("RS DECODE ERROR!  Padding position %d should be 0 but it was set to %02x.\n", derrlocs[i], rs_block[derrlocs[i]]);
-			}
-			derrors = -1;
-			break;
-		}
-	}
-
-	if (il2p_get_debug() >= 3) {
-		Debugprintf("==============================  il2p_decode_rs  returns %d  ==============================\n", derrors);
-	}
-	return (derrors);
-}
-
-// end il2p_init.c
-
-
-
-
-
-
-
-
-
-
-
-
-
-void ENCODE_RS(struct rs * rs, DTYPE * data, DTYPE * bb)
-{
-
-	int i, j;
-	DTYPE feedback;
-
-	memset(bb, 0, NROOTS * sizeof(DTYPE)); // clear out the FEC data area
-
-	for (i = 0; i < NN - NROOTS; i++) {
-		feedback = INDEX_OF[data[i] ^ bb[0]];
-		if (feedback != A0) {      /* feedback term is non-zero */
-			for (j = 1; j < NROOTS; j++)
-				bb[j] ^= ALPHA_TO[MODNN(feedback + GENPOLY[NROOTS - j])];
-		}
-		/* Shift */
-		memmove(&bb[0], &bb[1], sizeof(DTYPE)*(NROOTS - 1));
-		if (feedback != A0)
-			bb[NROOTS - 1] = ALPHA_TO[MODNN(feedback + GENPOLY[0])];
-		else
-			bb[NROOTS - 1] = 0;
-	}
-}
-
-
-
-
-int DECODE_RS(struct rs * rs, DTYPE * data, int *eras_pos, int no_eras) {
-
-	int deg_lambda, el, deg_omega;
-	int i, j, r, k;
-	DTYPE u, q, tmp, num1, num2, den, discr_r;
-	//  DTYPE lambda[NROOTS+1], s[NROOTS];	/* Err+Eras Locator poly and syndrome poly */
-	//  DTYPE b[NROOTS+1], t[NROOTS+1], omega[NROOTS+1];
-	//  DTYPE root[NROOTS], reg[NROOTS+1], loc[NROOTS];
-	DTYPE lambda[FX25_MAX_CHECK + 1], s[FX25_MAX_CHECK];	/* Err+Eras Locator poly and syndrome poly */
-	DTYPE b[FX25_MAX_CHECK + 1], t[FX25_MAX_CHECK + 1], omega[FX25_MAX_CHECK + 1];
-	DTYPE root[FX25_MAX_CHECK], reg[FX25_MAX_CHECK + 1], loc[FX25_MAX_CHECK];
-	int syn_error, count;
-
-	/* form the syndromes; i.e., evaluate data(x) at roots of g(x) */
-	for (i = 0; i < NROOTS; i++)
-		s[i] = data[0];
-
-	for (j = 1; j < NN; j++) {
-		for (i = 0; i < NROOTS; i++) {
-			if (s[i] == 0) {
-				s[i] = data[j];
-			}
-			else {
-				s[i] = data[j] ^ ALPHA_TO[MODNN(INDEX_OF[s[i]] + (FCR + i)*PRIM)];
-			}
-		}
-	}
-
-	/* Convert syndromes to index form, checking for nonzero condition */
-	syn_error = 0;
-	for (i = 0; i < NROOTS; i++) {
-		syn_error |= s[i];
-		s[i] = INDEX_OF[s[i]];
-	}
-
-	// fprintf(stderr,"syn_error = %4x\n",syn_error);
-	if (!syn_error) {
-		/* if syndrome is zero, data[] is a codeword and there are no
-		 * errors to correct. So return data[] unmodified
-		 */
-		count = 0;
-		goto finish;
-	}
-	memset(&lambda[1], 0, NROOTS * sizeof(lambda[0]));
-	lambda[0] = 1;
-
-	if (no_eras > 0) {
-		/* Init lambda to be the erasure locator polynomial */
-		lambda[1] = ALPHA_TO[MODNN(PRIM*(NN - 1 - eras_pos[0]))];
-		for (i = 1; i < no_eras; i++) {
-			u = MODNN(PRIM*(NN - 1 - eras_pos[i]));
-			for (j = i + 1; j > 0; j--) {
-				tmp = INDEX_OF[lambda[j - 1]];
-				if (tmp != A0)
-					lambda[j] ^= ALPHA_TO[MODNN(u + tmp)];
-			}
-		}
-
-#if DEBUG >= 1
-		/* Test code that verifies the erasure locator polynomial just constructed
-		   Needed only for decoder debugging. */
-
-		   /* find roots of the erasure location polynomial */
-		for (i = 1; i <= no_eras; i++)
-			reg[i] = INDEX_OF[lambda[i]];
-
-		count = 0;
-		for (i = 1, k = IPRIM - 1; i <= NN; i++, k = MODNN(k + IPRIM)) {
-			q = 1;
-			for (j = 1; j <= no_eras; j++)
-				if (reg[j] != A0) {
-					reg[j] = MODNN(reg[j] + j);
-					q ^= ALPHA_TO[reg[j]];
-				}
-			if (q != 0)
-				continue;
-			/* store root and error location number indices */
-			root[count] = i;
-			loc[count] = k;
-			count++;
-		}
-		if (count != no_eras) {
-			fprintf(stderr, "count = %d no_eras = %d\n lambda(x) is WRONG\n", count, no_eras);
-			count = -1;
-			goto finish;
-		}
-#if DEBUG >= 2
-		fprintf(stderr, "\n Erasure positions as determined by roots of Eras Loc Poly:\n");
-		for (i = 0; i < count; i++)
-			fprintf(stderr, "%d ", loc[i]);
-		fprintf(stderr, "\n");
-#endif
-#endif
-	}
-	for (i = 0; i < NROOTS + 1; i++)
-		b[i] = INDEX_OF[lambda[i]];
-
-	/*
-	 * Begin Berlekamp-Massey algorithm to determine error+erasure
-	 * locator polynomial
-	 */
-	r = no_eras;
-	el = no_eras;
-	while (++r <= NROOTS) {	/* r is the step number */
-	  /* Compute discrepancy at the r-th step in poly-form */
-		discr_r = 0;
-		for (i = 0; i < r; i++) {
-			if ((lambda[i] != 0) && (s[r - i - 1] != A0)) {
-				discr_r ^= ALPHA_TO[MODNN(INDEX_OF[lambda[i]] + s[r - i - 1])];
-			}
-		}
-		discr_r = INDEX_OF[discr_r];	/* Index form */
-		if (discr_r == A0) {
-			/* 2 lines below: B(x) <-- x*B(x) */
-			memmove(&b[1], b, NROOTS * sizeof(b[0]));
-			b[0] = A0;
-		}
-		else {
-			/* 7 lines below: T(x) <-- lambda(x) - discr_r*x*b(x) */
-			t[0] = lambda[0];
-			for (i = 0; i < NROOTS; i++) {
-				if (b[i] != A0)
-					t[i + 1] = lambda[i + 1] ^ ALPHA_TO[MODNN(discr_r + b[i])];
-				else
-					t[i + 1] = lambda[i + 1];
-			}
-			if (2 * el <= r + no_eras - 1) {
-				el = r + no_eras - el;
-				/*
-				 * 2 lines below: B(x) <-- inv(discr_r) *
-				 * lambda(x)
-				 */
-				for (i = 0; i <= NROOTS; i++)
-					b[i] = (lambda[i] == 0) ? A0 : MODNN(INDEX_OF[lambda[i]] - discr_r + NN);
-			}
-			else {
-				/* 2 lines below: B(x) <-- x*B(x) */
-				memmove(&b[1], b, NROOTS * sizeof(b[0]));
-				b[0] = A0;
-			}
-			memcpy(lambda, t, (NROOTS + 1) * sizeof(t[0]));
-		}
-	}
-
-	/* Convert lambda to index form and compute deg(lambda(x)) */
-	deg_lambda = 0;
-	for (i = 0; i < NROOTS + 1; i++) {
-		lambda[i] = INDEX_OF[lambda[i]];
-		if (lambda[i] != A0)
-			deg_lambda = i;
-	}
-	/* Find roots of the error+erasure locator polynomial by Chien search */
-	memcpy(&reg[1], &lambda[1], NROOTS * sizeof(reg[0]));
-	count = 0;		/* Number of roots of lambda(x) */
-	for (i = 1, k = IPRIM - 1; i <= NN; i++, k = MODNN(k + IPRIM)) {
-		q = 1; /* lambda[0] is always 0 */
-		for (j = deg_lambda; j > 0; j--) {
-			if (reg[j] != A0) {
-				reg[j] = MODNN(reg[j] + j);
-				q ^= ALPHA_TO[reg[j]];
-			}
-		}
-		if (q != 0)
-			continue; /* Not a root */
-		  /* store root (index-form) and error location number */
-#if DEBUG>=2
-		fprintf(stderr, "count %d root %d loc %d\n", count, i, k);
-#endif
-		root[count] = i;
-		loc[count] = k;
-		/* If we've already found max possible roots,
-		 * abort the search to save time
-		 */
-		if (++count == deg_lambda)
-			break;
-	}
-	if (deg_lambda != count) {
-		/*
-		 * deg(lambda) unequal to number of roots => uncorrectable
-		 * error detected
-		 */
-		count = -1;
-		goto finish;
-	}
-	/*
-	 * Compute err+eras evaluator poly omega(x) = s(x)*lambda(x) (modulo
-	 * x**NROOTS). in index form. Also find deg(omega).
-	 */
-	deg_omega = 0;
-	for (i = 0; i < NROOTS; i++) {
-		tmp = 0;
-		j = (deg_lambda < i) ? deg_lambda : i;
-		for (; j >= 0; j--) {
-			if ((s[i - j] != A0) && (lambda[j] != A0))
-				tmp ^= ALPHA_TO[MODNN(s[i - j] + lambda[j])];
-		}
-		if (tmp != 0)
-			deg_omega = i;
-		omega[i] = INDEX_OF[tmp];
-	}
-	omega[NROOTS] = A0;
-
-	/*
-	 * Compute error values in poly-form. num1 = omega(inv(X(l))), num2 =
-	 * inv(X(l))**(FCR-1) and den = lambda_pr(inv(X(l))) all in poly-form
-	 */
-	for (j = count - 1; j >= 0; j--) {
-		num1 = 0;
-		for (i = deg_omega; i >= 0; i--) {
-			if (omega[i] != A0)
-				num1 ^= ALPHA_TO[MODNN(omega[i] + i * root[j])];
-		}
-		num2 = ALPHA_TO[MODNN(root[j] * (FCR - 1) + NN)];
-		den = 0;
-
-		/* lambda[i+1] for i even is the formal derivative lambda_pr of lambda[i] */
-		for (i = min(deg_lambda, NROOTS - 1) & ~1; i >= 0; i -= 2) {
-			if (lambda[i + 1] != A0)
-				den ^= ALPHA_TO[MODNN(lambda[i + 1] + i * root[j])];
-		}
-		if (den == 0) {
-#if DEBUG >= 1
-			fprintf(stderr, "\n ERROR: denominator = 0\n");
-#endif
-			count = -1;
-			goto finish;
-		}
-		/* Apply error to data */
-		if (num1 != 0) {
-			data[loc[j]] ^= ALPHA_TO[MODNN(INDEX_OF[num1] + INDEX_OF[num2] + NN - INDEX_OF[den])];
-		}
-	}
-finish:
-	if (eras_pos != NULL) {
-		for (i = 0; i < count; i++)
-			eras_pos[i] = loc[i];
-	}
-	return count;
-}
-
-
-
-
-struct rs *INIT_RS(unsigned int symsize, unsigned int gfpoly, unsigned fcr, unsigned prim,
-	unsigned int nroots) {
-	struct rs *rs;
-	int i, j, sr, root, iprim;
-
-	if (symsize > 8 * sizeof(DTYPE))
-		return NULL; /* Need version with ints rather than chars */
-
-	if (fcr >= (1 << symsize))
-		return NULL;
-	if (prim == 0 || prim >= (1 << symsize))
-		return NULL;
-	if (nroots >= (1 << symsize))
-		return NULL; /* Can't have more roots than symbol values! */
-
-	rs = (struct rs *)calloc(1, sizeof(struct rs));
-	if (rs == NULL) {
-		Debugprintf("FATAL ERROR: Out of memory.\n");
-		exit(0);
-	}
-	rs->mm = symsize;
-	rs->nn = (1 << symsize) - 1;
-
-	rs->alpha_to = (DTYPE *)calloc((rs->nn + 1), sizeof(DTYPE));
-	if (rs->alpha_to == NULL) {
-		Debugprintf("FATAL ERROR: Out of memory.\n");
-		exit(0);
-	}
-	rs->index_of = (DTYPE *)calloc((rs->nn + 1), sizeof(DTYPE));
-	if (rs->index_of == NULL) {
-		Debugprintf("FATAL ERROR: Out of memory.\n");
-		exit(0);
-	}
-
-	/* Generate Galois field lookup tables */
-	rs->index_of[0] = A0; /* log(zero) = -inf */
-	rs->alpha_to[A0] = 0; /* alpha**-inf = 0 */
-	sr = 1;
-	for (i = 0; i < rs->nn; i++) {
-		rs->index_of[sr] = i;
-		rs->alpha_to[i] = sr;
-		sr <<= 1;
-		if (sr & (1 << symsize))
-			sr ^= gfpoly;
-		sr &= rs->nn;
-	}
-	if (sr != 1) {
-		/* field generator polynomial is not primitive! */
-		free(rs->alpha_to);
-		free(rs->index_of);
-		free(rs);
-		return NULL;
-	}
-
-	/* Form RS code generator polynomial from its roots */
-	rs->genpoly = (DTYPE *)calloc((nroots + 1), sizeof(DTYPE));
-	if (rs->genpoly == NULL) {
-		Debugprintf("FATAL ERROR: Out of memory.\n");
-		exit(0);
-	}
-	rs->fcr = fcr;
-	rs->prim = prim;
-	rs->nroots = nroots;
-
-	/* Find prim-th root of 1, used in decoding */
-	for (iprim = 1; (iprim % prim) != 0; iprim += rs->nn)
-		;
-	rs->iprim = iprim / prim;
-
-	rs->genpoly[0] = 1;
-	for (i = 0, root = fcr * prim; i < nroots; i++, root += prim) {
-		rs->genpoly[i + 1] = 1;
-
-		/* Multiply rs->genpoly[] by  @**(root + x) */
-		for (j = i; j > 0; j--) {
-			if (rs->genpoly[j] != 0)
-				rs->genpoly[j] = rs->genpoly[j - 1] ^ rs->alpha_to[modnn(rs, rs->index_of[rs->genpoly[j]] + root)];
-			else
-				rs->genpoly[j] = rs->genpoly[j - 1];
-		}
-		/* rs->genpoly[0] can never be zero */
-		rs->genpoly[0] = rs->alpha_to[modnn(rs, rs->index_of[rs->genpoly[0]] + root)];
-	}
-	/* convert rs->genpoly[] to index form for quicker encoding */
-	for (i = 0; i <= nroots; i++) {
-		rs->genpoly[i] = rs->index_of[rs->genpoly[i]];
-	}
-
-	// diagnostic prints
-#if 0
-	printf("Alpha To:\n\r");
-	for (i = 0; i < sizeof(DTYPE)*(rs->nn + 1); i++)
-		printf("0x%2x,", rs->alpha_to[i]);
-	printf("\n\r");
-
-	printf("Index Of:\n\r");
-	for (i = 0; i < sizeof(DTYPE)*(rs->nn + 1); i++)
-		printf("0x%2x,", rs->index_of[i]);
-	printf("\n\r");
-
-	printf("GenPoly:\n\r");
-	for (i = 0; i <= nroots; i++)
-		printf("0x%2x,", rs->genpoly[i]);
-	printf("\n\r");
-#endif
-	return rs;
-}
-
-
-// TEMPORARY!!!
-// FIXME: We already have multiple copies of this.
-// Consolidate them into one somewhere.
-
-void fx_hex_dump(unsigned char *p, int len)
-{
-	int n, i, offset;
-
-	offset = 0;
-	while (len > 0) {
-		n = len < 16 ? len : 16;
-		Debugprintf("  %03x: ", offset);
-		for (i = 0; i < n; i++) {
-			Debugprintf(" %02x", p[i]);
-		}
-		for (i = n; i < 16; i++) {
-			Debugprintf("   ");
-		}
-		Debugprintf("  ");
-		for (i = 0; i < n; i++) {
-			Debugprintf("%c", isprint(p[i]) ? p[i] : '.');
-		}
-		Debugprintf("\n");
-		p += 16;
-		offset += 16;
-		len -= 16;
-	}
-}
-
-
-/*-------------------------------------------------------------
- *
- * File:	il2p_codec.c
- *
- * Purpose:	Convert IL2P encoded format from and to direwolf internal packet format.
- *
- *--------------------------------------------------------------*/
-
-
- /*-------------------------------------------------------------
-  *
-  * Name:	il2p_encode_frame
-  *
-  * Purpose:	Convert AX.25 frame to IL2P encoding.
-  *
-  * Inputs:	chan	- Audio channel number, 0 = first.
-  *
-  *		pp	- Packet object pointer.
-  *
-  *		max_fec	- 1 to send maximum FEC size rather than automatic.
-  *
-  * Outputs:	iout	- Encoded result, excluding the 3 byte sync word.
-  *			  Caller should provide  IL2P_MAX_PACKET_SIZE  bytes.
-  *
-  * Returns:	Number of bytes for transmission.
-  *		-1 is returned for failure.
-  *
-  * Description:	Encode into IL2P format.
-  *
-  * Errors:	If something goes wrong, return -1.
-  *
-  *		Most likely reason is that the frame is too large.
-  *		IL2P has a max payload size of 1023 bytes.
-  *		For a type 1 header, this is the maximum AX.25 Information part size.
-  *		For a type 0 header, this is the entire AX.25 frame.
-  *
-  *--------------------------------------------------------------*/
-
-int il2p_encode_frame(packet_t pp, int max_fec, unsigned char *iout)
-{
-
-	// Can a type 1 header be used?
-
-	unsigned char hdr[IL2P_HEADER_SIZE + IL2P_HEADER_PARITY];
-	int e;
-	int out_len = 0;
-
-	e = il2p_type_1_header(pp, max_fec, hdr);
-	if (e >= 0) {
-		il2p_scramble_block(hdr, iout, IL2P_HEADER_SIZE);
-		il2p_encode_rs(iout, IL2P_HEADER_SIZE, IL2P_HEADER_PARITY, iout + IL2P_HEADER_SIZE);
-		out_len = IL2P_HEADER_SIZE + IL2P_HEADER_PARITY;
-
-		if (e == 0) {
-			// Success. No info part.
-			return (out_len);
-		}
-
-		// Payload is AX.25 info part.
-		unsigned char *pinfo;
-		int info_len;
-		info_len = ax25_get_info(pp, &pinfo);
-
-		int k = il2p_encode_payload(pinfo, info_len, max_fec, iout + out_len);
-		if (k > 0) {
-			out_len += k;
-			// Success. Info part was <= 1023 bytes.
-			return (out_len);
-		}
-
-		// Something went wrong with the payload encoding.
-		return (-1);
-	}
-	else if (e == -1) {
-
-		// Could not use type 1 header for some reason.
-		// e.g. More than 2 addresses, extended (mod 128) sequence numbers, etc.
-
-		e = il2p_type_0_header(pp, max_fec, hdr);
-		if (e > 0) {
-
-			il2p_scramble_block(hdr, iout, IL2P_HEADER_SIZE);
-			il2p_encode_rs(iout, IL2P_HEADER_SIZE, IL2P_HEADER_PARITY, iout + IL2P_HEADER_SIZE);
-			out_len = IL2P_HEADER_SIZE + IL2P_HEADER_PARITY;
-
-			// Payload is entire AX.25 frame.
-
-			unsigned char *frame_data_ptr = ax25_get_frame_data_ptr(pp);
-			int frame_len = ax25_get_frame_len(pp);
-			int k = il2p_encode_payload(frame_data_ptr, frame_len, max_fec, iout + out_len);
-			if (k > 0) {
-				out_len += k;
-				// Success. Entire AX.25 frame <= 1023 bytes.
-				return (out_len);
-			}
-			// Something went wrong with the payload encoding.
-			return (-1);
-		}
-		else if (e == 0) {
-			// Impossible condition.  Type 0 header must have payload.
-			return (-1);
-		}
-		else {
-			// AX.25 frame is too large.
-			return (-1);
-		}
-	}
-
-	// AX.25 Information part is too large.
-	return (-1);
-}
-
-
-
-/*-------------------------------------------------------------
- *
- * Name:	il2p_decode_frame
- *
- * Purpose:	Convert IL2P encoding to AX.25 frame.
- *		This is only used during testing, with a whole encoded frame.
- *		During reception, the header would have FEC and descrambling
- *		applied first so we would know how much to collect for the payload.
- *
- * Inputs:	irec	- Received IL2P frame excluding the 3 byte sync word.
- *
- * Future Out:	Number of symbols corrected.
- *
- * Returns:	Packet pointer or NULL for error.
- *
- *--------------------------------------------------------------*/
-
-packet_t il2p_decode_frame(unsigned char *irec)
-{
-	unsigned char uhdr[IL2P_HEADER_SIZE];		// After FEC and descrambling.
-	int e = il2p_clarify_header(irec, uhdr);
-
-	// TODO?: for symmetry we might want to clarify the payload before combining.
-
-	return (il2p_decode_header_payload(uhdr, irec + IL2P_HEADER_SIZE + IL2P_HEADER_PARITY, &e));
-}
-
-
-/*-------------------------------------------------------------
- *
- * Name:	il2p_decode_header_payload
- *
- * Purpose:	Convert IL2P encoding to AX.25 frame
- *
- * Inputs:	uhdr 		- Received header after FEC and descrambling.
- *		epayload	- Encoded payload.
- *
- * In/Out:	symbols_corrected - Symbols (bytes) corrected in the header.
- *				  Should be 0 or 1 because it has 2 parity symbols.
- *				  Here we add number of corrections for the payload.
- *
- * Returns:	Packet pointer or NULL for error.
- *
- *--------------------------------------------------------------*/
-
-packet_t il2p_decode_header_payload(unsigned char* uhdr, unsigned char *epayload, int *symbols_corrected)
-{
-	int hdr_type;
-	int max_fec;
-	int payload_len = il2p_get_header_attributes(uhdr, &hdr_type, &max_fec);
-
-	packet_t pp = NULL;
-
-	if (hdr_type == 1) {
-
-		// Header type 1.  Any payload is the AX.25 Information part.
-
-		pp = il2p_decode_header_type_1(uhdr, *symbols_corrected);
-		if (pp == NULL) {
-			// Failed for some reason.
-			return (NULL);
-		}
-
-		if (payload_len > 0) {
-			// This is the AX.25 Information part.
-
-			unsigned char extracted[IL2P_MAX_PAYLOAD_SIZE];
-			int e = il2p_decode_payload(epayload, payload_len, max_fec, extracted, symbols_corrected);
-
-			// It would be possible to have a good header but too many errors in the payload.
-
-			if (e <= 0) {
-				ax25_delete(pp);
-				pp = NULL;
-				return (pp);
-			}
-
-			if (e != payload_len) {
-				Debugprintf("IL2P Internal Error: %s(): hdr_type=%d, max_fec=%d, payload_len=%d, e=%d.\n", __func__, hdr_type, max_fec, payload_len, e);
-			}
-
-			ax25_set_info(pp, extracted, payload_len);
-		}
-		return (pp);
-	}
-	else {
-
-		// Header type 0.  The payload is the entire AX.25 frame.
-
-		unsigned char extracted[IL2P_MAX_PAYLOAD_SIZE];
-		int e = il2p_decode_payload(epayload, payload_len, max_fec, extracted, symbols_corrected);
-
-		if (e <= 0) {	// Payload was not received correctly.
-			return (NULL);
-		}
-
-		if (e != payload_len) {
-			Debugprintf("IL2P Internal Error: %s(): hdr_type=%d, e=%d, payload_len=%d\n", __func__, hdr_type, e, payload_len);
-			return (NULL);
-		}
-
-		alevel_t alevel;
-		memset(&alevel, 0, sizeof(alevel));
-		//alevel = demod_get_audio_level (chan, subchan); 	// What TODO? We don't know channel here.
-						// I think alevel gets filled in somewhere later making
-						// this redundant.
-
-		pp = ax25_from_frame(extracted, payload_len, alevel);
-		return (pp);
-	}
-
-} // end il2p_decode_header_payload
-
-// end il2p_codec.c
-
-
-
-/*--------------------------------------------------------------------------------
- *
- * File:	il2p_header.c
- *
- * Purpose:	Functions to deal with the IL2P header.
- *
- * Reference:	http://tarpn.net/t/il2p/il2p-specification0-4.pdf
- *
- *--------------------------------------------------------------------------------*/
-
-
-
- // Convert ASCII to/from DEC SIXBIT as defined here:
- // https://en.wikipedia.org/wiki/Six-bit_character_code#DEC_six-bit_code
-
-static inline int ascii_to_sixbit(int a)
-{
-	if (a >= ' ' && a <= '_') return (a - ' ');
-	return (31);	// '?' for any invalid.
-}
-
-static inline int sixbit_to_ascii(int s)
-{
-	return (s + ' ');
-}
-
-// Functions for setting the various header fields.
-// It is assumed that it was zeroed first so only the '1' bits are set.
-
-static void set_field(unsigned char *hdr, int bit_num, int lsb_index, int width, int value)
-{
-	while (width > 0 && value != 0) {
-		//assert(lsb_index >= 0 && lsb_index <= 11);
-		if (value & 1) {
-			hdr[lsb_index] |= 1 << bit_num;
-		}
-		value >>= 1;
-		lsb_index--;
-		width--;
-	}
-	//assert(value == 0);
-}
-
-#define SET_UI(hdr,val) set_field(hdr, 6, 0, 1, val)
-
-#define SET_PID(hdr,val) set_field(hdr, 6, 4, 4, val)
-
-#define SET_CONTROL(hdr,val) set_field(hdr, 6, 11, 7, val)
-
-
-#define SET_FEC_LEVEL(hdr,val) set_field(hdr, 7, 0, 1, val)
-
-#define SET_HDR_TYPE(hdr,val) set_field(hdr, 7, 1, 1, val)
-
-#define SET_PAYLOAD_BYTE_COUNT(hdr,val) set_field(hdr, 7, 11, 10, val)
-
-
-// Extracting the fields.
-
-static int get_field(unsigned char *hdr, int bit_num, int lsb_index, int width)
-{
-	int result = 0;
-	lsb_index -= width - 1;
-	while (width > 0) {
-		result <<= 1;
-		//assert(lsb_index >= 0 && lsb_index <= 11);
-		if (hdr[lsb_index] & (1 << bit_num)) {
-			result |= 1;
-		}
-		lsb_index++;
-		width--;
-	}
-	return (result);
-}
-
-#define GET_UI(hdr) get_field(hdr, 6, 0, 1)
-
-#define GET_PID(hdr) get_field(hdr, 6, 4, 4)
-
-#define GET_CONTROL(hdr) get_field(hdr, 6, 11, 7)
-
-
-#define GET_FEC_LEVEL(hdr) get_field(hdr, 7, 0, 1)
-
-#define GET_HDR_TYPE(hdr) get_field(hdr, 7, 1, 1)
-
-#define GET_PAYLOAD_BYTE_COUNT(hdr) get_field(hdr, 7, 11, 10)
-
-
-
-// AX.25 'I' and 'UI' frames have a protocol ID which determines how the
-// information part should be interpreted.
-// Here we squeeze the most common cases down to 4 bits.
-// Return -1 if translation is not possible.  Fall back to type 0 header in this case.
-
-static int encode_pid(packet_t pp)
-{
-	int pid = ax25_get_pid(pp);
-
-	if ((pid & 0x30) == 0x20) return (0x2);		// AX.25 Layer 3
-	if ((pid & 0x30) == 0x10) return (0x2);		// AX.25 Layer 3
-	if (pid == 0x01) return (0x3);			// ISO 8208 / CCIT X.25 PLP
-	if (pid == 0x06) return (0x4);			// Compressed TCP/IP
-	if (pid == 0x07) return (0x5);			// Uncompressed TCP/IP
-	if (pid == 0x08) return (0x6);			// Segmentation fragmen
-	if (pid == 0xcc) return (0xb);			// ARPA Internet Protocol
-	if (pid == 0xcd) return (0xc);			// ARPA Address Resolution
-	if (pid == 0xce) return (0xd);			// FlexNet
-	if (pid == 0xcf) return (0xe);			// TheNET
-	if (pid == 0xf0) return (0xf);			// No L3
-	return (-1);
-}
-
-// Convert IL2P 4 bit PID to AX.25 8 bit PID.
-
-
-static int decode_pid(int pid)
-{
-	static const unsigned char axpid[16] = {
-	0xf0,			// Should not happen. 0 is for 'S' frames.
-	0xf0,			// Should not happen. 1 is for 'U' frames (but not UI).
-	0x20,			// AX.25 Layer 3
-	0x01,			// ISO 8208 / CCIT X.25 PLP
-	0x06,			// Compressed TCP/IP
-	0x07,			// Uncompressed TCP/IP
-	0x08,			// Segmentation fragment
-	0xf0,			// Future
-	0xf0,			// Future
-	0xf0,			// Future
-	0xf0,			// Future
-	0xcc,			// ARPA Internet Protocol
-	0xcd,			// ARPA Address Resolution
-	0xce,			// FlexNet
-	0xcf,			// TheNET
-	0xf0 };			// No L3
-
-	//assert(pid >= 0 && pid <= 15);
-	return (axpid[pid]);
-}
-
-
-
-/*--------------------------------------------------------------------------------
- *
- * Function:	il2p_type_1_header
- *
- * Purpose:	Attempt to create type 1 header from packet object.
- *
- * Inputs:	pp	- Packet object.
- *
- *		max_fec	- 1 to use maximum FEC symbols , 0 for automatic.
- *
- * Outputs:	hdr	- IL2P header with no scrambling or parity symbols.
- *			  Must be large enough to hold IL2P_HEADER_SIZE unsigned bytes.
- *
- * Returns:	Number of bytes for information part or -1 for failure.
- *		In case of failure, fall back to type 0 transparent encapsulation.
- *
- * Description:	Type 1 Headers do not support AX.25 repeater callsign addressing,
- *		Modulo-128 extended mode window sequence numbers, nor any callsign
- *		characters that cannot translate to DEC SIXBIT.
- *		If these cases are encountered during IL2P packet encoding,
- *		the encoder switches to Type 0 Transparent Encapsulation.
- *		SABME can't be handled by type 1.
- *
- *--------------------------------------------------------------------------------*/
-
-int il2p_type_1_header(packet_t pp, int max_fec, unsigned char *hdr)
-{
-	memset(hdr, 0, IL2P_HEADER_SIZE);
-
-	if (ax25_get_num_addr(pp) != 2) {
-		// Only two addresses are allowed for type 1 header.
-		return (-1);
-	}
-
-	// Check does not apply for 'U' frames but put in one place rather than two.
-
-	if (ax25_get_modulo(pp) == 128) return(-1);
-
-	// Destination and source addresses go into low bits 0-5 for bytes 0-11.
-
-	char dst_addr[AX25_MAX_ADDR_LEN];
-	char src_addr[AX25_MAX_ADDR_LEN];
-
-	ax25_get_addr_no_ssid(pp, AX25_DESTINATION, dst_addr);
-	int dst_ssid = ax25_get_ssid(pp, AX25_DESTINATION);
-
-	ax25_get_addr_no_ssid(pp, AX25_SOURCE, src_addr);
-	int src_ssid = ax25_get_ssid(pp, AX25_SOURCE);
-
-	unsigned char *a = (unsigned char *)dst_addr;
-	for (int i = 0; *a != '\0'; i++, a++) {
-		if (*a < ' ' || *a > '_') {
-			// Shouldn't happen but follow the rule.
-			return (-1);
-		}
-		hdr[i] = ascii_to_sixbit(*a);
-	}
-
-	a = (unsigned char *)src_addr;
-	for (int i = 6; *a != '\0'; i++, a++) {
-		if (*a < ' ' || *a > '_') {
-			// Shouldn't happen but follow the rule.
-			return (-1);
-		}
-		hdr[i] = ascii_to_sixbit(*a);
-	}
-
-	// Byte 12 has DEST SSID in upper nybble and SRC SSID in lower nybble and 
-	hdr[12] = (dst_ssid << 4) | src_ssid;
-
-	ax25_frame_type_t frame_type;
-	cmdres_t cr;			// command or response.
-	char description[64];
-	int pf;				// Poll/Final.
-	int nr, ns;			// Sequence numbers.
-
-	frame_type = ax25_frame_type(pp, &cr, description, &pf, &nr, &ns);
-
-	//Debugprintf ("%s(): %s-%d>%s-%d: %s\n", __func__, src_addr, src_ssid, dst_addr, dst_ssid, description);
-
-	switch (frame_type) {
-
-	case frame_type_S_RR:		// Receive Ready - System Ready To Receive
-	case frame_type_S_RNR:		// Receive Not Ready - TNC Buffer Full
-	case frame_type_S_REJ:		// Reject Frame - Out of Sequence or Duplicate
-	case frame_type_S_SREJ:		// Selective Reject - Request single frame repeat
-
-		// S frames (RR, RNR, REJ, SREJ), mod 8, have control N(R) P/F S S 0 1
-		// These are mapped into    P/F N(R) C S S
-		// Bit 6 is not mentioned in documentation but it is used for P/F for the other frame types.
-		// C is copied from the C bit in the destination addr.
-		// C from source is not used here.  Reception assumes it is the opposite.
-		// PID is set to 0, meaning none, for S frames.
-
-		SET_UI(hdr, 0);
-		SET_PID(hdr, 0);
-		SET_CONTROL(hdr, (pf << 6) | (nr << 3) | (((cr == cr_cmd) | (cr == cr_11)) << 2));
-
-		// This gets OR'ed into the above.
-		switch (frame_type) {
-		case frame_type_S_RR:	SET_CONTROL(hdr, 0);	break;
-		case frame_type_S_RNR:	SET_CONTROL(hdr, 1);	break;
-		case frame_type_S_REJ:	SET_CONTROL(hdr, 2);	break;
-		case frame_type_S_SREJ:	SET_CONTROL(hdr, 3);	break;
-		default:	break;
-		}
-
-		break;
-
-	case frame_type_U_SABM:		// Set Async Balanced Mode
-	case frame_type_U_DISC:		// Disconnect
-	case frame_type_U_DM:		// Disconnect Mode
-	case frame_type_U_UA:		// Unnumbered Acknowledge
-	case frame_type_U_FRMR:		// Frame Reject
-	case frame_type_U_UI:		// Unnumbered Information
-	case frame_type_U_XID:		// Exchange Identification
-	case frame_type_U_TEST:		// Test
-
-		// The encoding allows only 3 bits for frame type and SABME got left out.
-		// Control format:  P/F opcode[3] C n/a n/a
-		// The grayed out n/a bits are observed as 00 in the example.
-		// The header UI field must also be set for UI frames.
-		// PID is set to 1 for all U frames other than UI.
-
-		if (frame_type == frame_type_U_UI) {
-			SET_UI(hdr, 1);	// I guess this is how we distinguish 'I' and 'UI'
-				// on the receiving end.
-			int pid = encode_pid(pp);
-			if (pid < 0) return (-1);
-			SET_PID(hdr, pid);
-		}
-		else {
-			SET_PID(hdr, 1);	// 1 for 'U' other than 'UI'.
-		}
-
-		// Each of the destination and source addresses has a "C" bit.
-		// They should normally have the opposite setting.
-		// IL2P has only a single bit to represent 4 possbilities.
-		//
-		//	dst	src	il2p	meaning
-		//	---	---	----	-------
-		//	0	0	0	Not valid (earlier protocol version)
-		//	1	0	1	Command (v2)
-		//	0	1	0	Response (v2)
-		//	1	1	1	Not valid (earlier protocol version)
-		//
-		// APRS does not mention how to set these bits and all 4 combinations
-		// are seen in the wild.  Apparently these are ignored on receive and no
-		// one cares.  Here we copy from the C bit in the destination address.
-		// It should be noted that the case of both C bits being the same can't
-		// be represented so the il2p encode/decode bit not produce exactly the
-		// same bits.  We see this in the second example in the protocol spec.
-		// The original UI frame has both C bits of 0 so it is received as a response.
-
-		SET_CONTROL(hdr, (pf << 6) | (((cr == cr_cmd) | (cr == cr_11)) << 2));
-
-		// This gets OR'ed into the above.
-		switch (frame_type) {
-		case frame_type_U_SABM:	SET_CONTROL(hdr, 0 << 3);	break;
-		case frame_type_U_DISC:	SET_CONTROL(hdr, 1 << 3);	break;
-		case frame_type_U_DM:	SET_CONTROL(hdr, 2 << 3);	break;
-		case frame_type_U_UA:	SET_CONTROL(hdr, 3 << 3);	break;
-		case frame_type_U_FRMR:	SET_CONTROL(hdr, 4 << 3);	break;
-		case frame_type_U_UI:	SET_CONTROL(hdr, 5 << 3);	break;
-		case frame_type_U_XID:	SET_CONTROL(hdr, 6 << 3);	break;
-		case frame_type_U_TEST:	SET_CONTROL(hdr, 7 << 3);	break;
-		default:	break;
-		}
-		break;
-
-	case frame_type_I:		// Information
-
-		// I frames (mod 8 only)
-		// encoded control: P/F N(R) N(S)
-
-		SET_UI(hdr, 0);
-
-		int pid2 = encode_pid(pp);
-		if (pid2 < 0) return (-1);
-		SET_PID(hdr, pid2);
-
-		SET_CONTROL(hdr, (pf << 6) | (nr << 3) | ns);
-		break;
-
-	case frame_type_U_SABME:		// Set Async Balanced Mode, Extended
-	case frame_type_U:			// other Unnumbered, not used by AX.25.
-	case frame_not_AX25:		// Could not get control byte from frame.
-	default:
-
-		// Fall back to the header type 0 for these.
-		return (-1);
-	}
-
-	// Common for all header type 1.
-
-		// Bit 7 has [FEC Level:1], [HDR Type:1], [Payload byte Count:10]
-
-	SET_FEC_LEVEL(hdr, max_fec);
-	SET_HDR_TYPE(hdr, 1);
-
-	unsigned char *pinfo;
-	int info_len;
-
-	info_len = ax25_get_info(pp, &pinfo);
-	if (info_len < 0 || info_len > IL2P_MAX_PAYLOAD_SIZE) {
-		return (-2);
-	}
-
-	SET_PAYLOAD_BYTE_COUNT(hdr, info_len);
-	return (info_len);
-}
-
-
-// This should create a packet from the IL2P header.
-// The information part will not be filled in.
-
-static void trim(char *stuff)
-{
-	char *p = stuff + strlen(stuff) - 1;
-	while (strlen(stuff) > 0 && (*p == ' ')) {
-		*p = '\0';
-		p--;
-	}
-}
-
-
-
-/*--------------------------------------------------------------------------------
- *
- * Function:	il2p_decode_header_type_1
- *
- * Purpose:	Attempt to convert type 1 header to a packet object.
- *
- * Inputs:	hdr - IL2P header with no scrambling or parity symbols.
- *
- *		num_sym_changed - Number of symbols changed by FEC in the header.
- *				Should be 0 or 1.
- *
- * Returns:	Packet Object or NULL for failure.
- *
- * Description:	A later step will process the payload for the information part.
- *
- *--------------------------------------------------------------------------------*/
-
-packet_t il2p_decode_header_type_1(unsigned char *hdr, int num_sym_changed)
-{
-
-	if (GET_HDR_TYPE(hdr) != 1) {
-		Debugprintf("IL2P Internal error.  Should not be here: %s, when header type is 0.\n", __func__);
-		return (NULL);
-	}
-
-	// First get the addresses including SSID.
-
-	char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN];
-	int num_addr = 2;
-	memset(addrs, 0, 2 * AX25_MAX_ADDR_LEN);
-
-	// The IL2P header uses 2 parity symbols which means a single corrupted symbol (byte)
-	// can always be corrected.
-	// However, I have seen cases, where the error rate is very high, where the RS decoder
-	// thinks it found a valid code block by changing one symbol but it was the wrong one.
-	// The result is trash.  This shows up as address fields like 'R&G4"A' and 'TEW\ !'.
-	// I added a sanity check here to catch characters other than upper case letters and digits.
-	// The frame should be rejected in this case.  The question is whether to discard it
-	// silently or print a message so the user can see that something strange is happening?
-	// My current thinking is that it should be silently ignored if the header has been
-	// modified (correctee or more likely, made worse in this cases).
-	// If no changes were made, something weird is happening.  We should mention it for
-	// troubleshooting rather than sweeping it under the rug.
-
-	// The same thing has been observed with the payload, under very high error conditions,
-	// and max_fec==0.  Here I don't see a good solution.  AX.25 information can contain
-	// "binary" data so I'm not sure what sort of sanity check could be added.
-	// This was not observed with max_fec==1.  If we make that the default, same as Nino TNC,
-	// it would be extremely extremely unlikely unless someone explicitly selects weaker FEC.
-
-	// TODO: We could do something similar for header type 0.
-	// The address fields should be all binary zero values.
-	// Someone overly ambitious might check the addresses found in the first payload block.
-
-	for (int i = 0; i <= 5; i++) {
-		addrs[AX25_DESTINATION][i] = sixbit_to_ascii(hdr[i] & 0x3f);
-	}
-	trim(addrs[AX25_DESTINATION]);
-	for (int i = 0; i < strlen(addrs[AX25_DESTINATION]); i++) {
-		if (!isupper(addrs[AX25_DESTINATION][i]) && !isdigit(addrs[AX25_DESTINATION][i])) {
-			if (num_sym_changed == 0) {
-				// This can pop up sporadically when receiving random noise.
-				// Would be better to show only when debug is enabled but variable not available here.
-				// TODO: For now we will just suppress it.
-					//text_color_set(DW_COLOR_ERROR);
-					//Debugprintf ("IL2P: Invalid character '%c' in destination address '%s'\n", addrs[AX25_DESTINATION][i], addrs[AX25_DESTINATION]);
-			}
-			return (NULL);
-		}
-	}
-	sprintf(addrs[AX25_DESTINATION] + strlen(addrs[AX25_DESTINATION]), "-%d", (hdr[12] >> 4) & 0xf);
-
-	for (int i = 0; i <= 5; i++) {
-		addrs[AX25_SOURCE][i] = sixbit_to_ascii(hdr[i + 6] & 0x3f);
-	}
-	trim(addrs[AX25_SOURCE]);
-	for (int i = 0; i < strlen(addrs[AX25_SOURCE]); i++) {
-		if (!isupper(addrs[AX25_SOURCE][i]) && !isdigit(addrs[AX25_SOURCE][i])) {
-			if (num_sym_changed == 0) {
-				// This can pop up sporadically when receiving random noise.
-				// Would be better to show only when debug is enabled but variable not available here.
-				// TODO: For now we will just suppress it.
-					//text_color_set(DW_COLOR_ERROR);
-					//Debugprintf ("IL2P: Invalid character '%c' in source address '%s'\n", addrs[AX25_SOURCE][i], addrs[AX25_SOURCE]);
-			}
-			return (NULL);
-		}
-	}
-	sprintf(addrs[AX25_SOURCE] + strlen(addrs[AX25_SOURCE]), "-%d", hdr[12] & 0xf);
-
-	// The PID field gives us the general type.
-	// 0 = 'S' frame.
-	// 1 = 'U' frame other than UI.
-	// others are either 'UI' or 'I' depending on the UI field.
-
-	int pid = GET_PID(hdr);
-	int ui = GET_UI(hdr);
-
-	if (pid == 0) {
-
-		// 'S' frame.
-		// The control field contains: P/F N(R) C S S
-
-		int control = GET_CONTROL(hdr);
-		cmdres_t cr = (control & 0x04) ? cr_cmd : cr_res;
-		ax25_frame_type_t ftype;
-		switch (control & 0x03) {
-		case 0: ftype = frame_type_S_RR; break;
-		case 1: ftype = frame_type_S_RNR; break;
-		case 2: ftype = frame_type_S_REJ; break;
-		default: ftype = frame_type_S_SREJ; break;
-		}
-		int modulo = 8;
-		int nr = (control >> 3) & 0x07;
-		int pf = (control >> 6) & 0x01;
-		unsigned char *pinfo = NULL;	// Any info for SREJ will be added later.
-		int info_len = 0;
-		return (ax25_s_frame(addrs, num_addr, cr, ftype, modulo, nr, pf, pinfo, info_len));
-	}
-	else if (pid == 1) {
-
-		// 'U' frame other than 'UI'.
-		// The control field contains: P/F OPCODE{3) C x x
-
-		int control = GET_CONTROL(hdr);
-		cmdres_t cr = (control & 0x04) ? cr_cmd : cr_res;
-		int axpid = 0;	// unused for U other than UI.
-		ax25_frame_type_t ftype;
-		switch ((control >> 3) & 0x7) {
-		case 0: ftype = frame_type_U_SABM; break;
-		case 1: ftype = frame_type_U_DISC; break;
-		case 2: ftype = frame_type_U_DM; break;
-		case 3: ftype = frame_type_U_UA; break;
-		case 4: ftype = frame_type_U_FRMR; break;
-		case 5: ftype = frame_type_U_UI; axpid = 0xf0; break;		// Should not happen with IL2P pid == 1.
-		case 6: ftype = frame_type_U_XID; break;
-		default: ftype = frame_type_U_TEST; break;
-		}
-		int pf = (control >> 6) & 0x01;
-		unsigned char *pinfo = NULL;	// Any info for UI, XID, TEST will be added later.
-		int info_len = 0;
-		return (ax25_u_frame(addrs, num_addr, cr, ftype, pf, axpid, pinfo, info_len));
-	}
-	else if (ui) {
-
-		// 'UI' frame.
-		// The control field contains: P/F OPCODE{3) C x x
-
-		int control = GET_CONTROL(hdr);
-		cmdres_t cr = (control & 0x04) ? cr_cmd : cr_res;
-		ax25_frame_type_t ftype = frame_type_U_UI;
-		int pf = (control >> 6) & 0x01;
-		int axpid = decode_pid(GET_PID(hdr));
-		unsigned char *pinfo = NULL;	// Any info for UI, XID, TEST will be added later.
-		int info_len = 0;
-		return (ax25_u_frame(addrs, num_addr, cr, ftype, pf, axpid, pinfo, info_len));
-	}
-	else {
-
-		// 'I' frame.
-		// The control field contains: P/F N(R) N(S)
-
-		int control = GET_CONTROL(hdr);
-		cmdres_t cr = cr_cmd;		// Always command.
-		int pf = (control >> 6) & 0x01;
-		int nr = (control >> 3) & 0x7;
-		int ns = control & 0x7;
-		int modulo = 8;
-		int axpid = decode_pid(GET_PID(hdr));
-		unsigned char *pinfo = NULL;	// Any info for UI, XID, TEST will be added later.
-		int info_len = 0;
-		return (ax25_i_frame(addrs, num_addr, cr, modulo, nr, ns, pf, axpid, pinfo, info_len));
-	}
-	return (NULL);	// unreachable but avoid warning.
-
-} // end
-
-
-/*--------------------------------------------------------------------------------
- *
- * Function:	il2p_type_0_header
- *
- * Purpose:	Attempt to create type 0 header from packet object.
- *
- * Inputs:	pp	- Packet object.
- *
- *		max_fec	- 1 to use maximum FEC symbols, 0 for automatic.
- *
- * Outputs:	hdr	- IL2P header with no scrambling or parity symbols.
- *			  Must be large enough to hold IL2P_HEADER_SIZE unsigned bytes.
- *
- * Returns:	Number of bytes for information part or -1 for failure.
- *		In case of failure, fall back to type 0 transparent encapsulation.
- *
- * Description:	The type 0 header is used when it is not one of the restricted cases
- *		covered by the type 1 header.
- *		The AX.25 frame is put in the payload.
- *		This will cover: more than one address, mod 128 sequences, etc.
- *
- *--------------------------------------------------------------------------------*/
-
-int il2p_type_0_header(packet_t pp, int max_fec, unsigned char *hdr)
-{
-	memset(hdr, 0, IL2P_HEADER_SIZE);
-
-	// Bit 7 has [FEC Level:1], [HDR Type:1], [Payload byte Count:10]
-
-	SET_FEC_LEVEL(hdr, max_fec);
-	SET_HDR_TYPE(hdr, 0);
-
-	int frame_len = ax25_get_frame_len(pp);
-
-	if (frame_len < 14 || frame_len > IL2P_MAX_PAYLOAD_SIZE) {
-		return (-2);
-	}
-
-	SET_PAYLOAD_BYTE_COUNT(hdr, frame_len);
-	return (frame_len);
-}
-
-
-/***********************************************************************************
- *
- * Name:        il2p_get_header_attributes
- *
- * Purpose:     Extract a few attributes from an IL2p header.
- *
- * Inputs:      hdr	- IL2P header structure.
- *
- * Outputs:     hdr_type - 0 or 1.
- *
- *		max_fec	- 0 for automatic or 1 for fixed maximum size.
- *
- * Returns:	Payload byte count.   (actual payload size, not the larger encoded format)
- *
- ***********************************************************************************/
-
-
-int il2p_get_header_attributes(unsigned char *hdr, int *hdr_type, int *max_fec)
-{
-	*hdr_type = GET_HDR_TYPE(hdr);
-	*max_fec = GET_FEC_LEVEL(hdr);
-	return(GET_PAYLOAD_BYTE_COUNT(hdr));
-}
-
-
-/***********************************************************************************
- *
- * Name:        il2p_clarify_header
- *
- * Purpose:     Convert received header to usable form.
- *		This involves RS FEC then descrambling.
- *
- * Inputs:      rec_hdr	- Header as received over the radio.
- *
- * Outputs:     corrected_descrambled_hdr - After RS FEC and unscrambling.
- *
- * Returns:	Number of symbols that were corrected:
- *		 0 = No errors
- *		 1 = Single symbol corrected.
- *		 <0 = Unable to obtain good header.
- *
- ***********************************************************************************/
-
-int il2p_clarify_header(unsigned char *rec_hdr, unsigned char *corrected_descrambled_hdr)
-{
-	unsigned char corrected[IL2P_HEADER_SIZE + IL2P_HEADER_PARITY];
-
-	int e = il2p_decode_rs(rec_hdr, IL2P_HEADER_SIZE, IL2P_HEADER_PARITY, corrected);
-
-	il2p_descramble_block(corrected, corrected_descrambled_hdr, IL2P_HEADER_SIZE);
-
-	return (e);
-}
-
-// end il2p_header.c 
-
-
-/*--------------------------------------------------------------------------------
- *
- * File:	il2p_payload.c
- *
- * Purpose:	Functions dealing with the payload.
- *
- *--------------------------------------------------------------------------------*/
-
-
- /*--------------------------------------------------------------------------------
-  *
-  * Function:	il2p_payload_compute
-  *
-  * Purpose:	Compute number and sizes of data blocks based on total size.
-  *
-  * Inputs:	payload_size	0 to 1023.  (IL2P_MAX_PAYLOAD_SIZE)
-  *		max_fec		true for 16 parity symbols, false for automatic.
-  *
-  * Outputs:	*p		Payload block sizes and counts.
-  *				Number of parity symbols per block.
-  *
-  * Returns:	Number of bytes in the encoded format.
-  *		Could be 0 for no payload blocks.
-  *		-1 for error (i.e. invalid unencoded size: <0 or >1023)
-  *
-  *--------------------------------------------------------------------------------*/
-
-int il2p_payload_compute(il2p_payload_properties_t *p, int payload_size, int max_fec)
-{
-	memset(p, 0, sizeof(il2p_payload_properties_t));
-
-	if (payload_size < 0 || payload_size > IL2P_MAX_PAYLOAD_SIZE) {
-		return (-1);
-	}
-	if (payload_size == 0) {
-		return (0);
-	}
-
-	if (max_fec) {
-		p->payload_byte_count = payload_size;
-		p->payload_block_count = (p->payload_byte_count + 238) / 239;
-		p->small_block_size = p->payload_byte_count / p->payload_block_count;
-		p->large_block_size = p->small_block_size + 1;
-		p->large_block_count = p->payload_byte_count - (p->payload_block_count * p->small_block_size);
-		p->small_block_count = p->payload_block_count - p->large_block_count;
-		p->parity_symbols_per_block = 16;
-	}
-	else {
-		p->payload_byte_count = payload_size;
-		p->payload_block_count = (p->payload_byte_count + 246) / 247;
-		p->small_block_size = p->payload_byte_count / p->payload_block_count;
-		p->large_block_size = p->small_block_size + 1;
-		p->large_block_count = p->payload_byte_count - (p->payload_block_count * p->small_block_size);
-		p->small_block_count = p->payload_block_count - p->large_block_count;
-		//p->parity_symbols_per_block = (p->small_block_size / 32) + 2;  // Looks like error in documentation
-
-		// It would work if the number of parity symbols was based on large block size.
-
-		if (p->small_block_size <= 61) p->parity_symbols_per_block = 2;
-		else if (p->small_block_size <= 123) p->parity_symbols_per_block = 4;
-		else if (p->small_block_size <= 185) p->parity_symbols_per_block = 6;
-		else if (p->small_block_size <= 247) p->parity_symbols_per_block = 8;
-		else {
-			// Should not happen.  But just in case...
-			Debugprintf("IL2P parity symbol per payload block error.  small_block_size = %d\n", p->small_block_size);
-			return (-1);
-		}
-	}
-
-	// Return the total size for the encoded format.
-
-	return (p->small_block_count * (p->small_block_size + p->parity_symbols_per_block) +
-		p->large_block_count * (p->large_block_size + p->parity_symbols_per_block));
-
-} // end il2p_payload_compute
-
-
-
-/*--------------------------------------------------------------------------------
- *
- * Function:	il2p_encode_payload
- *
- * Purpose:	Split payload into multiple blocks such that each set
- *		of data and parity symbols fit into a 255 byte RS block.
- *
- * Inputs:	*payload	Array of bytes.
- *		payload_size	0 to 1023.  (IL2P_MAX_PAYLOAD_SIZE)
- *		max_fec		true for 16 parity symbols, false for automatic.
- *
- * Outputs:	*enc		Encoded payload for transmission.
- *				Up to IL2P_MAX_ENCODED_SIZE bytes.
- *
- * Returns:	-1 for error (i.e. invalid size)
- *		0 for no blocks.  (i.e. size zero)
- *		Number of bytes generated.  Maximum IL2P_MAX_ENCODED_SIZE.
- *
- * Note:	I interpreted the protocol spec as saying the LFSR state is retained
- *		between data blocks.  During interoperability testing, I found that
- *		was not the case.  It is reset for each data block.
- *
- *--------------------------------------------------------------------------------*/
-
-
-int il2p_encode_payload(unsigned char *payload, int payload_size, int max_fec, unsigned char *enc)
-{
-	if (payload_size > IL2P_MAX_PAYLOAD_SIZE) return (-1);
-	if (payload_size == 0) return (0);
-
-	// Determine number of blocks and sizes.
-
-	il2p_payload_properties_t ipp;
-	int e;
-	e = il2p_payload_compute(&ipp, payload_size, max_fec);
-	if (e <= 0) {
-		return (e);
-	}
-
-	unsigned char *pin = payload;
-	unsigned char *pout = enc;
-	int encoded_length = 0;
-	unsigned char scram[256];
-	unsigned char parity[IL2P_MAX_PARITY_SYMBOLS];
-
-	// First the large blocks.
-
-	for (int b = 0; b < ipp.large_block_count; b++) {
-
-		il2p_scramble_block(pin, scram, ipp.large_block_size);
-		memcpy(pout, scram, ipp.large_block_size);
-		pin += ipp.large_block_size;
-		pout += ipp.large_block_size;
-		encoded_length += ipp.large_block_size;
-		il2p_encode_rs(scram, ipp.large_block_size, ipp.parity_symbols_per_block, parity);
-		memcpy(pout, parity, ipp.parity_symbols_per_block);
-		pout += ipp.parity_symbols_per_block;
-		encoded_length += ipp.parity_symbols_per_block;
-	}
-
-	// Then the small blocks.
-
-	for (int b = 0; b < ipp.small_block_count; b++) {
-
-		il2p_scramble_block(pin, scram, ipp.small_block_size);
-		memcpy(pout, scram, ipp.small_block_size);
-		pin += ipp.small_block_size;
-		pout += ipp.small_block_size;
-		encoded_length += ipp.small_block_size;
-		il2p_encode_rs(scram, ipp.small_block_size, ipp.parity_symbols_per_block, parity);
-		memcpy(pout, parity, ipp.parity_symbols_per_block);
-		pout += ipp.parity_symbols_per_block;
-		encoded_length += ipp.parity_symbols_per_block;
-	}
-
-	return (encoded_length);
-
-} // end il2p_encode_payload
-
-
-/*--------------------------------------------------------------------------------
- *
- * Function:	il2p_decode_payload
- *
- * Purpose:	Extract original data from encoded payload.
- *
- * Inputs:	received	Array of bytes.  Size is unknown but in practice it
- *				must not exceed IL2P_MAX_ENCODED_SIZE.
- *		payload_size	0 to 1023.  (IL2P_MAX_PAYLOAD_SIZE)
- *				Expected result size based on header.
- *		max_fec		true for 16 parity symbols, false for automatic.
- *
- * Outputs:	payload_out	Recovered payload.
- *
- * In/Out:	symbols_corrected	Number of symbols corrected.
- *
- *
- * Returns:	Number of bytes extracted.  Should be same as payload_size going in.
- *		-3 for unexpected internal inconsistency.
- *		-2 for unable to recover from signal corruption.
- *		-1 for invalid size.
- *		0 for no blocks.  (i.e. size zero)
- *
- * Description:	Each block is scrambled separately but the LSFR state is carried
- *		from the first payload block to the next.
- *
- *--------------------------------------------------------------------------------*/
-
-int il2p_decode_payload(unsigned char *received, int payload_size, int max_fec, unsigned char *payload_out, int *symbols_corrected)
-{
-	// Determine number of blocks and sizes.
-
-	il2p_payload_properties_t ipp;
-	int e;
-	e = il2p_payload_compute(&ipp, payload_size, max_fec);
-	if (e <= 0) {
-		return (e);
-	}
-
-	unsigned char *pin = received;
-	unsigned char *pout = payload_out;
-	int decoded_length = 0;
-	int failed = 0;
-
-	// First the large blocks.
-
-	for (int b = 0; b < ipp.large_block_count; b++) {
-		unsigned char corrected_block[255];
-		int e = il2p_decode_rs(pin, ipp.large_block_size, ipp.parity_symbols_per_block, corrected_block);
-
-		// Debugprintf ("%s:%d: large block decode_rs returned status = %d\n", __FILE__, __LINE__, e);
-
-		if (e < 0) failed = 1;
-		*symbols_corrected += e;
-
-		il2p_descramble_block(corrected_block, pout, ipp.large_block_size);
-
-		if (il2p_get_debug() >= 2) {
-	
-			Debugprintf("Descrambled large payload block, %d bytes:\n", ipp.large_block_size);
-			fx_hex_dump(pout, ipp.large_block_size);
-		}
-
-		pin += ipp.large_block_size + ipp.parity_symbols_per_block;
-		pout += ipp.large_block_size;
-		decoded_length += ipp.large_block_size;
-	}
-
-	// Then the small blocks.
-
-	for (int b = 0; b < ipp.small_block_count; b++) {
-		unsigned char corrected_block[255];
-		int e = il2p_decode_rs(pin, ipp.small_block_size, ipp.parity_symbols_per_block, corrected_block);
-
-		// Debugprintf ("%s:%d: small block decode_rs returned status = %d\n", __FILE__, __LINE__, e);
-
-		if (e < 0) failed = 1;
-		*symbols_corrected += e;
-
-		il2p_descramble_block(corrected_block, pout, ipp.small_block_size);
-
-		if (il2p_get_debug() >= 2) {
-	
-			Debugprintf("Descrambled small payload block, %d bytes:\n", ipp.small_block_size);
-			fx_hex_dump(pout, ipp.small_block_size);
-		}
-
-		pin += ipp.small_block_size + ipp.parity_symbols_per_block;
-		pout += ipp.small_block_size;
-		decoded_length += ipp.small_block_size;
-	}
-
-	if (failed) {
-		//Debugprintf ("%s:%d: failed = %0x\n", __FILE__, __LINE__, failed);
-		return (-2);
-	}
-
-	if (decoded_length != payload_size) {
-		Debugprintf("IL2P Internal error: decoded_length = %d, payload_size = %d\n", decoded_length, payload_size);
-		return (-3);
-	}
-
-	return (decoded_length);
-
-} // end il2p_decode_payload
-
-// end il2p_payload.c
-
-
-
-struct il2p_context_s {
-
-	enum { IL2P_SEARCHING = 0, IL2P_HEADER, IL2P_PAYLOAD, IL2P_DECODE } state;
-
-	unsigned int acc;	// Accumulate most recent 24 bits for sync word matching.
-				// Lower 8 bits are also used for accumulating bytes for
-				// the header and payload.
-
-	int bc;			// Bit counter so we know when a complete byte has been accumulated.
-
-	int polarity;		// 1 if opposite of expected polarity.
-
-	unsigned char shdr[IL2P_HEADER_SIZE + IL2P_HEADER_PARITY];
-	// Scrambled header as received over the radio.  Includes parity.
-	int hc;			// Number if bytes placed in above.
-
-	unsigned char uhdr[IL2P_HEADER_SIZE];  // Header after FEC and unscrambling.
-
-	int eplen;		// Encoded payload length.  This is not the nuumber from
-				// from the header but rather the number of encoded bytes to gather.
-
-	unsigned char spayload[IL2P_MAX_ENCODED_PAYLOAD_SIZE];
-	// Scrambled and encoded payload as received over the radio.
-	int pc;			// Number of bytes placed in above.
-
-	int corrected;		// Number of symbols corrected by RS FEC.
-};
-
-static struct il2p_context_s *il2p_context[MAX_CHANS][MAX_SUBCHANS][MAX_SLICERS];
-
-
-
-/***********************************************************************************
- *
- * Name:        il2p_rec_bit
- *
- * Purpose:     Extract FX.25 packets from a stream of bits.
- *
- * Inputs:      chan    - Channel number.
- *
- *              subchan - This allows multiple demodulators per channel.
- *
- *              slice   - Allows multiple slicers per demodulator (subchannel).
- *
- *              dbit	- One bit from the received data stream.
- *
- * Description: This is called once for each received bit.
- *              For each valid packet, process_rec_frame() is called for further processing.
- *		It can gather multiple candidates from different parallel demodulators
- *		("subchannels") and slicers, then decide which one is the best.
- *
- ***********************************************************************************/
-
-int centreFreq[4] = { 0, 0, 0, 0 };
-
-void il2p_rec_bit(int chan, int subchan, int slice, int dbit)
-{
-	// Allocate context blocks only as needed.
-
-	if (dbit)
-		dbit = 1;
-
-	struct il2p_context_s *F = il2p_context[chan][subchan][slice];
-	if (F == NULL) {
-		//assert(chan >= 0 && chan < MAX_CHANS);
-		//assert(subchan >= 0 && subchan < MAX_SUBCHANS);
-		//assert(slice >= 0 && slice < MAX_SLICERS);
-		F = il2p_context[chan][subchan][slice] = (struct il2p_context_s *)malloc(sizeof(struct il2p_context_s));
-		//assert(F != NULL);
-		memset(F, 0, sizeof(struct il2p_context_s));
-	}
-
-	// Accumulate most recent 24 bits received.  Most recent is LSB.
-
-	F->acc = ((F->acc << 1) | (dbit & 1)) & 0x00ffffff;
-
-	// State machine to look for sync word then gather appropriate number of header and payload bytes.
-
-	switch (F->state) {
-
-	case IL2P_SEARCHING:		// Searching for the sync word.
-
-		if (__builtin_popcount(F->acc ^ IL2P_SYNC_WORD) <= 1) {	// allow single bit mismatch
-		  //text_color_set (DW_COLOR_INFO);
-		  //Debugprintf ("IL2P header has normal polarity\n");
-			F->polarity = 0;
-			F->state = IL2P_HEADER;
-			F->bc = 0;
-			F->hc = 0;
-		
-			// Determine Centre Freq
-			
-			centreFreq[chan] = GuessCentreFreq(chan);
-		}
-		else if (__builtin_popcount((~F->acc & 0x00ffffff) ^ IL2P_SYNC_WORD) <= 1) {
-			// FIXME - this pops up occasionally with random noise.  Find better way to convey information.
-			// This also happens for each slicer - to noisy.
-			//Debugprintf ("IL2P header has reverse polarity\n");
-			F->polarity = 1;
-			F->state = IL2P_HEADER;
-			F->bc = 0;
-			F->hc = 0;
-			centreFreq[chan] = GuessCentreFreq(chan);
-		}
-			
-		break;
-
-	case IL2P_HEADER:		// Gathering the header.
-
-		F->bc++;
-		if (F->bc == 8) {	// full byte has been collected.
-			F->bc = 0;
-			if (!F->polarity) {
-				F->shdr[F->hc++] = F->acc & 0xff;
-			}
-			else {
-				F->shdr[F->hc++] = (~F->acc) & 0xff;
-			}
-			if (F->hc == IL2P_HEADER_SIZE + IL2P_HEADER_PARITY) {		// Have all of header
-
-				//if (il2p_get_debug() >= 1)
-				//{
-				//	Debugprintf("IL2P header as received [%d.%d.%d]:\n", chan, subchan, slice);
-				//	fx_hex_dump(F->shdr, IL2P_HEADER_SIZE + IL2P_HEADER_PARITY);
-				//}
-
-				// Fix any errors and descramble.
-				F->corrected = il2p_clarify_header(F->shdr, F->uhdr);
-
-				if (F->corrected >= 0) {	// Good header.
-							// How much payload is expected?
-					il2p_payload_properties_t plprop;
-					int hdr_type, max_fec;
-					int len = il2p_get_header_attributes(F->uhdr, &hdr_type, &max_fec);
-
-					F->eplen = il2p_payload_compute(&plprop, len, max_fec);
-
-					if (il2p_get_debug() >= 1)
-					{	
-						Debugprintf("Header type %d, max fec = %d", hdr_type, max_fec);
-						Debugprintf("Need to collect %d encoded bytes for %d byte payload.", F->eplen, len);
-						Debugprintf("%d small blocks of %d and %d large blocks of %d.  %d parity symbols per block",
-							plprop.small_block_count, plprop.small_block_size,
-							plprop.large_block_count, plprop.large_block_size, plprop.parity_symbols_per_block);
-					}
-
-					if (F->eplen >= 1) {		// Need to gather payload.
-						F->pc = 0;
-						F->state = IL2P_PAYLOAD;
-					}
-					else if (F->eplen == 0) {	// No payload.
-						F->pc = 0;
-						F->state = IL2P_DECODE;
-					}
-					else {			// Error.
-
-						if (il2p_get_debug() >= 1) {
-							Debugprintf("IL2P header INVALID.\n");
-						}
-
-						F->state = IL2P_SEARCHING;
-					}
-				}  // good header after FEC.
-				else {
-					F->state = IL2P_SEARCHING;	// Header failed FEC check.
-				}
-			}  // entire header has been collected.    
-		}  // full byte collected.
-		break;
-
-	case IL2P_PAYLOAD:		// Gathering the payload, if any.
-
-		F->bc++;
-		if (F->bc == 8) {	// full byte has been collected.
-			F->bc = 0;
-			if (!F->polarity) {
-				F->spayload[F->pc++] = F->acc & 0xff;
-			}
-			else {
-				F->spayload[F->pc++] = (~F->acc) & 0xff;
-			}
-			if (F->pc == F->eplen) {
-
-				// TODO?: for symmetry it seems like we should clarify the payload before combining.
-
-				F->state = IL2P_DECODE;
-			}
-		}
-		break;
-
-	case IL2P_DECODE:
-		// We get here after a good header and any payload has been collected.
-		// Processing is delayed by one bit but I think it makes the logic cleaner.
-		// During unit testing be sure to send an extra bit to flush it out at the end.
-
-		// in uhdr[IL2P_HEADER_SIZE];  // Header after FEC and descrambling.
-
-		// TODO?:  for symmetry, we might decode the payload here and later build the frame.
-
-	{
-		packet_t pp = il2p_decode_header_payload(F->uhdr, F->spayload, &(F->corrected));
-
-		if (il2p_get_debug() >= 1)
-		{
-			if (pp == NULL)
-			{
-				// Most likely too many FEC errors.
-				Debugprintf("FAILED to construct frame in %s.\n", __func__);
-			}
-		}
-
-		if (pp != NULL) {
-			alevel_t alevel = demod_get_audio_level(chan, subchan);
-			retry_t retries = F->corrected;
-			int is_fx25 = 1;		// FIXME: distinguish fx.25 and IL2P.
-					  // Currently this just means that a FEC mode was used.
-
-			// TODO: Could we put last 3 arguments in packet object rather than passing around separately?
-
-			multi_modem_process_rec_packet(chan, subchan, slice, pp, alevel, retries, is_fx25, slice, centreFreq[chan]);
-		}
-	}   // end block for local variables.
-
-	if (il2p_get_debug() >= 1) {
-
-		Debugprintf("-----");
-	}
-
-	F->state = IL2P_SEARCHING;
-	break;
-
-	} // end of switch
-
-} // end il2p_rec_bit
-
-
-
-
-
-
-
-// Scramble bits for il2p transmit.
-
-// Note that there is a delay of 5 until the first bit comes out.
-// So we need to need to ignore the first 5 out and stick in
-// an extra 5 filler bits to flush at the end.
-
-#define INIT_TX_LSFR 0x00f
-
-static inline int scramble_bit(int in, int *state)
-{
-	int out = ((*state >> 4) ^ *state) & 1;
-	*state = ((((in ^ *state) & 1) << 9) | (*state ^ ((*state & 1) << 4))) >> 1;
-	return (out);
-}
-
-
-// Undo data scrambling for il2p receive.
-
-#define INIT_RX_LSFR 0x1f0
-
-static inline int descramble_bit(int in, int *state)
-{
-	int out = (in ^ *state) & 1;
-	*state = ((*state >> 1) | ((in & 1) << 8)) ^ ((in & 1) << 3);
-	return (out);
-}
-
-
-/*--------------------------------------------------------------------------------
- *
- * Function:	il2p_scramble_block
- *
- * Purpose:	Scramble a block before adding RS parity.
- *
- * Inputs:	in		Array of bytes.
- *		len		Number of bytes both in and out.
- *
- * Outputs:	out		Array of bytes.
- *
- *--------------------------------------------------------------------------------*/
-
-void il2p_scramble_block(unsigned char *in, unsigned char *out, int len)
-{
-	int tx_lfsr_state = INIT_TX_LSFR;
-
-	memset(out, 0, len);
-
-	int skipping = 1;	// Discard the first 5 out.
-	int ob = 0;		// Index to output byte.
-	int om = 0x80;		// Output bit mask;
-	for (int ib = 0; ib < len; ib++) {
-		for (int im = 0x80; im != 0; im >>= 1) {
-			int s = scramble_bit((in[ib] & im) != 0, &tx_lfsr_state);
-			if (ib == 0 && im == 0x04) skipping = 0;
-			if (!skipping) {
-				if (s) {
-					out[ob] |= om;
-				}
-				om >>= 1;
-				if (om == 0) {
-					om = 0x80;
-					ob++;
-				}
-			}
-		}
-	}
-	// Flush it.
-
-	// This is a relic from when I thought the state would need to
-	// be passed along for the next block.
-	// Preserve the LSFR state from before flushing.
-	// This might be needed as the initial state for later payload blocks.
-	int x = tx_lfsr_state;
-	for (int n = 0; n < 5; n++) {
-		int s = scramble_bit(0, &x);
-		if (s) {
-			out[ob] |= om;
-		}
-		om >>= 1;
-		if (om == 0) {
-			om = 0x80;
-			ob++;
-		}
-	}
-
-}  // end il2p_scramble_block
-
-
-
-/*--------------------------------------------------------------------------------
- *
- * Function:	il2p_descramble_block
- *
- * Purpose:	Descramble a block after removing RS parity.
- *
- * Inputs:	in		Array of bytes.
- *		len		Number of bytes both in and out.
- *
- * Outputs:	out		Array of bytes.
- *
- *--------------------------------------------------------------------------------*/
-
-void il2p_descramble_block(unsigned char *in, unsigned char *out, int len)
-{
-	int rx_lfsr_state = INIT_RX_LSFR;
-
-	memset(out, 0, len);
-
-	for (int b = 0; b < len; b++) {
-		for (int m = 0x80; m != 0; m >>= 1) {
-			int d = descramble_bit((in[b] & m) != 0, &rx_lfsr_state);
-			if (d) {
-				out[b] |= m;
-			}
-		}
-	}
-}
-
-// end il2p_scramble.c
-
-
-
-
-static int number_of_bits_sent[MAX_CHANS];		// Count number of bits sent by "il2p_send_frame"
-
-static void send_bytes(int chan, unsigned char *b, int count, int polarity);
-static void send_bit(int chan, int b, int polarity);
-
-
-
-/*-------------------------------------------------------------
- *
- * Name:	il2p_send_frame
- *
- * Purpose:	Convert frames to a stream of bits in IL2P format.
- *
- * Inputs:	chan	- Audio channel number, 0 = first.
- *
- *		pp	- Pointer to packet object.
- *
- *		max_fec	- 1 to force 16 parity symbols for each payload block.
- *			  0 for automatic depending on block size.
- *
- *		polarity - 0 for normal.  1 to invert signal.
- *			   2 special case for testing - introduce some errors to test FEC.
- *
- * Outputs:	Bits are shipped out by calling tone_gen_put_bit().
- *
- * Returns:	Number of bits sent including
- *		- Preamble   (01010101...)
- *		- 3 byte Sync Word.
- *		- 15 bytes for Header.
- *		- Optional payload.
- *		The required time can be calculated by dividing this
- *		number by the transmit rate of bits/sec.
- *		-1 is returned for failure.
- *
- * Description:	Generate an IL2P encoded frame.
- *
- * Assumptions:	It is assumed that the tone_gen module has been
- *		properly initialized so that bits sent with
- *		tone_gen_put_bit() are processed correctly.
- *
- * Errors:	Return -1 for error.  Probably frame too large.
- *
- * Note:	Inconsistency here. ax25 version has just a byte array
- *		and length going in.  Here we need the full packet object.
- *
- *--------------------------------------------------------------*/
-
-string * il2p_send_frame(int chan, packet_t pp, int max_fec, int polarity)
-{
-	unsigned char encoded[IL2P_MAX_PACKET_SIZE];
-	string * packet = newString();
-	int preamblecount;
-	unsigned char preamble[1024];
-
-
-	encoded[0] = (IL2P_SYNC_WORD >> 16) & 0xff;
-	encoded[1] = (IL2P_SYNC_WORD >> 8) & 0xff;
-	encoded[2] = (IL2P_SYNC_WORD) & 0xff;
-
-	int elen = il2p_encode_frame(pp, max_fec, encoded + IL2P_SYNC_WORD_SIZE);
-	if (elen <= 0) {
-		Debugprintf("IL2P: Unable to encode frame into IL2P.\n");
-		return (packet);
-	}
-
-	elen += IL2P_SYNC_WORD_SIZE;
-
-	number_of_bits_sent[chan] = 0;
-
-	if (il2p_get_debug() >= 1) {
-		Debugprintf("IL2P frame, max_fec = %d, %d encoded bytes total", max_fec, elen);
-//		fx_hex_dump(encoded, elen);
-	}
-
-	// Send bits to modulator.
-
-	// Try using preaamble for txdelay
-
-	preamblecount = (txdelay[chan] * tx_baudrate[chan]) / 8000;		// 8 for bits, 1000 for mS
-
-	if (preamblecount > 1024)
-		preamblecount = 1024;
-
- 	memset(preamble, IL2P_PREAMBLE, preamblecount);
-
-	stringAdd(packet, preamble, preamblecount);
-	stringAdd(packet, encoded, elen);
-
-	tx_fx25_size[chan] = packet->Length * 8;
-
-	return packet;
-}
-
-
-
-// TX Code. Builds whole packet then sends a bit at a time
-
-#define TX_SILENCE 0
-#define TX_DELAY 1
-#define TX_TAIL 2
-#define TX_NO_DATA 3
-#define TX_FRAME 4
-#define TX_WAIT_BPF 5
-
-
-#define TX_BIT0 0
-#define TX_BIT1 1
-#define FRAME_EMPTY 0
-#define FRAME_FULL 1
-#define FRAME_NO_FRAME 2
-#define FRAME_NEW_FRAME 3
-#define BYTE_EMPTY 0
-#define BYTE_FULL 1
-
-extern UCHAR tx_frame_status[5];
-extern UCHAR tx_byte_status[5];
-extern string * tx_data[5];
-extern int tx_data_len[5];
-extern UCHAR tx_bit_stream[5];
-extern UCHAR tx_bit_cnt[5];
-extern long tx_tail_cnt[5];
-extern BOOL tx_bs_bit[5];
-
-string * fill_il2p_data(int snd_ch, string * data)
-{
-	string * result;
-	packet_t pp = ax25_new();
-	
-
-	// Call il2p_send_frame to build the bit stream
-
-	pp->frame_len = data->Length - 2;					// Included CRC
-	memcpy(pp->frame_data, data->Data, data->Length);
-
-	result = il2p_send_frame(snd_ch, pp, 1, 0);
-
-	return result;
-}
-
-
-
-void il2p_get_new_frame(int snd_ch, TStringList * frame_stream)
-{
-	string * myTemp;
-
-	tx_bs_bit[snd_ch] = 0;
-	tx_bit_cnt[snd_ch] = 0;
-	tx_fx25_size_cnt[snd_ch] = 0;
-	tx_fx25_size[snd_ch] = 1;
-	tx_frame_status[snd_ch] = FRAME_NEW_FRAME;
-	tx_byte_status[snd_ch] = BYTE_EMPTY;
-
-	if (frame_stream->Count == 0)
-		tx_frame_status[snd_ch] = FRAME_NO_FRAME;
-	else
-	{
-		// We now pass control byte and ack bytes on front and pointer to socket on end if ackmode
-
-		myTemp = Strings(frame_stream, 0);			// get message
-
-		if ((myTemp->Data[0] & 0x0f) == 12)			// ACKMODE
-		{
-			// Save copy then copy data up 3 bytes
-
-			Add(&KISS_acked[snd_ch], duplicateString(myTemp));
-
-			mydelete(myTemp, 0, 3);
-			myTemp->Length -= sizeof(void *);
-		}
-		else
-		{
-			// Just remove control 
-
-			mydelete(myTemp, 0, 1);
-		}
-
-		AGW_AX25_frame_analiz(snd_ch, FALSE, myTemp);
-		put_frame(snd_ch, myTemp, "", TRUE, FALSE);
-
-		tx_data[snd_ch] = fill_il2p_data(snd_ch, myTemp);
-
-		Delete(frame_stream, 0);			// This will invalidate temp
-	}
-}
-
-
-
-// Original code
-
-/*
-static void send_bytes(int chan, unsigned char *b, int count, int polarity)
-{
-	for (int j = 0; j < count; j++) {
-		unsigned int x = b[j];
-		for (int k = 0; k < 8; k++) {
-			send_bit(chan, (x & 0x80) != 0, polarity);
-			x <<= 1;
-		}
-	}
-}
-
-// NRZI would be applied for AX.25 but IL2P does not use it.
-// However we do have an option to invert the signal.
-// The direwolf receive implementation will automatically compensate
-// for either polarity but other implementations might not.
-
-static void send_bit(int chan, int b, int polarity)
-{
-	tone_gen_put_bit(chan, (b ^ polarity) & 1);
-	number_of_bits_sent[chan]++;
-}
-*/
-
-
-
-
-int il2p_get_new_bit(int snd_ch, Byte bit)
-{
-	string *s;
-
-	if (tx_frame_status[snd_ch] == FRAME_EMPTY)
-	{
-		il2p_get_new_frame(snd_ch, &all_frame_buf[snd_ch]);
-		if (tx_frame_status[snd_ch] == FRAME_NEW_FRAME)
-			tx_frame_status[snd_ch] = FRAME_FULL;
-	}
-
-	if (tx_frame_status[snd_ch] == FRAME_FULL)
-	{
-		if (tx_byte_status[snd_ch] == BYTE_EMPTY)
-		{
-			if (tx_data[snd_ch]->Length)
-			{
-				s = tx_data[snd_ch];
-
-				tx_bit_stream[snd_ch] = s->Data[0];
-				tx_frame_status[snd_ch] = FRAME_FULL;
-				tx_byte_status[snd_ch] = BYTE_FULL;
-				tx_bit_cnt[snd_ch] = 0;
-				mydelete(tx_data[snd_ch], 0, 1);
-			}
-			else
-				tx_frame_status[snd_ch] = FRAME_EMPTY;
-		}
-		if (tx_byte_status[snd_ch] == BYTE_FULL)
-		{
-			// il2p sends high order bit first
-
-			bit = tx_bit_stream[snd_ch] >> 7;			// top bit to bottom
-
-			tx_bit_stream[snd_ch] = tx_bit_stream[snd_ch] << 1;
-			tx_bit_cnt[snd_ch]++;
-			tx_fx25_size_cnt[snd_ch]++;
-			if (tx_bit_cnt[snd_ch] >= 8)
-				tx_byte_status[snd_ch] = BYTE_EMPTY;
-			if (tx_fx25_size_cnt[snd_ch] == tx_fx25_size[snd_ch])
-				tx_frame_status[snd_ch] = FRAME_EMPTY;
-		}
-	}
-
-	if (tx_frame_status[snd_ch] == FRAME_EMPTY)
-	{
-		il2p_get_new_frame(snd_ch, &all_frame_buf[snd_ch]);
-
-		switch (tx_frame_status[snd_ch])
-		{
-		case FRAME_NEW_FRAME:
-			tx_frame_status[snd_ch] = FRAME_FULL;
-			break;
-
-		case FRAME_NO_FRAME:
-			tx_tail_cnt[snd_ch] = 0;
-			tx_frame_status[snd_ch] = FRAME_EMPTY;
-			tx_status[snd_ch] = TX_TAIL;
-			break;
-		}
-	}
-	return bit;
-}
-
-
-
diff --git a/kiss.h b/kiss.h
deleted file mode 100644
index 1dc40da..0000000
--- a/kiss.h
+++ /dev/null
@@ -1,24 +0,0 @@
-
-/* 
- * Name:	kiss.h
- *
- * This is for the pseudo terminal KISS interface.
- */
-
-
-#include "ax25_pad.h"		/* for packet_t */
-
-#include "config.h"
-
-#include "kiss_frame.h"		// for struct kissport_status_s
-
-
-void kisspt_init (struct misc_config_s *misc_config);
-
-void kisspt_send_rec_packet (int chan, int kiss_cmd, unsigned char *fbuf,  int flen,
-		struct kissport_status_s *notused1, int notused2);
-
-void kisspt_set_debug (int n);
-
-
-/* end kiss.h */
diff --git a/kiss_frame.h b/kiss_frame.h
deleted file mode 100644
index 941f5c0..0000000
--- a/kiss_frame.h
+++ /dev/null
@@ -1,126 +0,0 @@
-
-/* kiss_frame.h */
-
-#ifndef KISS_FRAME_H
-#define KISS_FRAME_H
-
-
-#include "audio.h"		/* for struct audio_s */
-
-
-/*
- * The first byte of a KISS frame has:
- *	channel in upper nybble.
- *	command in lower nybble.
- */
-
-#define KISS_CMD_DATA_FRAME	0
-#define KISS_CMD_TXDELAY	1
-#define KISS_CMD_PERSISTENCE	2
-#define KISS_CMD_SLOTTIME	3
-#define KISS_CMD_TXTAIL		4
-#define KISS_CMD_FULLDUPLEX	5
-#define KISS_CMD_SET_HARDWARE	6
-#define XKISS_CMD_DATA		12	// Not supported. http://he.fi/pub/oh7lzb/bpq/multi-kiss.pdf
-#define XKISS_CMD_POLL		14	// Not supported.
-#define KISS_CMD_END_KISS	15
-
-
-
-/*
- * Special characters used by SLIP protocol.
- */
-
-#define FEND 0xC0
-#define FESC 0xDB
-#define TFEND 0xDC
-#define TFESC 0xDD
-
-
-
-enum kiss_state_e {
-	KS_SEARCHING = 0,	/* Looking for FEND to start KISS frame. */
-				/* Must be 0 so we can simply zero whole structure to initialize. */
-	KS_COLLECTING};		/* In process of collecting KISS frame. */
-
-
-#define MAX_KISS_LEN 2048	/* Spec calls for at least 1024. */
-				/* Might want to make it longer to accommodate */
-				/* maximum packet length. */
-
-#define MAX_NOISE_LEN 100
-
-typedef struct kiss_frame_s {
-	
-	enum kiss_state_e state;
-
-	unsigned char kiss_msg[MAX_KISS_LEN];
-				/* Leading FEND is optional. */
-				/* Contains escapes and ending FEND. */
-	int kiss_len;
-
-	unsigned char noise[MAX_NOISE_LEN];
-	int noise_len;
-
-} kiss_frame_t;
-
-
-// This is used only for TCPKISS but it put in kissnet.h,
-// there would be a circular dependency between the two header files.
-// Each KISS TCP port has its own status block.
-
-struct kissport_status_s {
-
-	struct kissport_status_s *pnext;	// To next in list.
-
-	volatile int arg2;			// temp for passing second arg into
-						// kissnet_listen_thread
-
-	int tcp_port;				// default 8001
-
-	int chan;				// Radio channel for this tcp port.
-						// -1 for all.
-
-	// The default is a limit of 3 client applications at the same time.
-	// You can increase the limit by changing the line below.
-	// A larger number consumes more resources so don't go crazy by making it larger than needed.
-	// TODO:  Should this be moved to direwolf.h so max number of audio devices
-	// client apps are in the same place?
-
-#define MAX_NET_CLIENTS 3
-
-	int client_sock[MAX_NET_CLIENTS];
-				/* File descriptor for socket for */
-				/* communication with client application. */
-				/* Set to -1 if not connected. */
-				/* (Don't use SOCKET type because it is unsigned.) */
-
-	kiss_frame_t kf[MAX_NET_CLIENTS];
-				/* Accumulated KISS frame and state of decoder. */
-};
-
-
-
-#ifndef KISSUTIL
-void kiss_frame_init (struct audio_s *pa);
-#endif
-
-int kiss_encapsulate (unsigned char *in, int ilen, unsigned char *out);
-
-int kiss_unwrap (unsigned char *in, int ilen, unsigned char *out);
-
-void kiss_rec_byte (kiss_frame_t *kf, unsigned char ch, int debug, struct kissport_status_s *kps, int client,
-			void (*sendfun)(int chan, int kiss_cmd, unsigned char *fbuf, int flen, struct kissport_status_s *onlykps, int onlyclient));
-
-typedef enum fromto_e { FROM_CLIENT=0, TO_CLIENT=1 } fromto_t;
-
-void kiss_process_msg (unsigned char *kiss_msg, int kiss_len, int debug, struct kissport_status_s *kps, int client,
-			void (*sendfun)(int chan, int kiss_cmd, unsigned char *fbuf, int flen, struct kissport_status_s *onlykps, int onlyclient));
-
-void kiss_debug_print (fromto_t fromto, char *special, unsigned char *pmsg, int msg_len);
-
-
-#endif  // KISS_FRAME_H
-
-
-/* end kiss_frame.h */
diff --git a/kissnet.h b/kissnet.h
deleted file mode 100644
index 469e4e6..0000000
--- a/kissnet.h
+++ /dev/null
@@ -1,29 +0,0 @@
-
-/* 
- * Name:	kissnet.h
- */
-
-#ifndef KISSNET_H
-#define KISSNET_H
-
-#include "ax25_pad.h"		/* for packet_t */
-
-#include "config.h"
-
-#include "kiss_frame.h"
-
-
-
-void kissnet_init (struct misc_config_s *misc_config);
-
-void kissnet_send_rec_packet (int chan, int kiss_cmd, unsigned char *fbuf,  int flen,
-			struct kissport_status_s *onlykps, int onlyclient);
-
-void kiss_net_set_debug (int n);
-
-void kissnet_copy (unsigned char *kiss_msg, int kiss_len, int chan, int cmd, struct kissport_status_s *from_kps, int from_client);
-
-
-#endif  // KISSNET_H
-
-/* end kissnet.h */
diff --git a/kissserial.h b/kissserial.h
deleted file mode 100644
index 44fb3c3..0000000
--- a/kissserial.h
+++ /dev/null
@@ -1,23 +0,0 @@
-
-/* 
- * Name:	kissserial.h
- */
-
-
-#include "ax25_pad.h"		/* for packet_t */
-
-#include "config.h"
-
-#include "kiss_frame.h"
-
-
-void kissserial_init (struct misc_config_s *misc_config);
-
-void kissserial_send_rec_packet (int chan, int kiss_cmd, unsigned char *fbuf,  int flen,
-		struct kissport_status_s *notused1, int notused2);
-
-
-void kissserial_set_debug (int n);
-
-
-/* end kissserial.h */
diff --git a/latlong.h b/latlong.h
deleted file mode 100644
index ae98fe6..0000000
--- a/latlong.h
+++ /dev/null
@@ -1,24 +0,0 @@
-
-/* latlong.h */
-
-
-/* Use this value for unknown latitude/longitude or other values. */
-
-#define G_UNKNOWN (-999999)
-
-
-void latitude_to_str (double dlat, int ambiguity, char *slat);
-void longitude_to_str (double dlong, int ambiguity, char *slong);
-
-void latitude_to_comp_str (double dlat, char *clat);
-void longitude_to_comp_str (double dlon, char *clon);
-
-void latitude_to_nmea (double dlat, char *slat, char *hemi);
-void longitude_to_nmea (double dlong, char *slong, char *hemi);
-
-double latitude_from_nmea (char *pstr, char *phemi);
-double longitude_from_nmea (char *pstr, char *phemi);
-
-double ll_distance_km (double lat1, double lon1, double lat2, double lon2);
-
-int ll_from_grid_square (char *maidenhead, double *dlat, double *dlon);
\ No newline at end of file
diff --git a/log.h b/log.h
deleted file mode 100644
index 3afb6b1..0000000
--- a/log.h
+++ /dev/null
@@ -1,19 +0,0 @@
-
-/* log.h */
-
-
-#include "hdlc_rec2.h"		// for retry_t
-
-#include "decode_aprs.h"	// for decode_aprs_t
-
-#include "ax25_pad.h"
-
-
-
-void log_init (int daily_names, char *path);
-
-void log_write (int chan, decode_aprs_t *A, packet_t pp, alevel_t alevel, retry_t retries);
-
-void log_rr_bits (decode_aprs_t *A, packet_t pp);
-
-void log_term (void); 	
\ No newline at end of file
diff --git a/main.cpp b/main.cpp
index fb343c1..43ea7cd 100644
--- a/main.cpp
+++ b/main.cpp
@@ -88,4 +88,3 @@ int main(int argc, char *argv[])
 
 }
 
-
diff --git a/mgn_icon.h b/mgn_icon.h
deleted file mode 100644
index c870bc0..0000000
--- a/mgn_icon.h
+++ /dev/null
@@ -1,276 +0,0 @@
-
-
-/* 
- * MGN_icon.h 
- *
- * Waypoint icon codes for use in the $PMGNWPL sentence.
- *
- * Derived from Data Transmission Protocol For Magellan Products - version 2.11, March 2003
- *
- * http://www.gpsinformation.org/mag-proto-2-11.pdf
- *
- *
- * That's 13 years ago.  There should be something newer available but I can't find it.
- *
- * The is based on the newer models at the time.  Earlier models had shorter incompatible icon lists.
- */
-
-
-
-#define MGN_crossed_square "a"
-#define MGN_box "b"
-#define MGN_house "c"
-#define MGN_aerial "d"
-#define MGN_airport "e"
-#define MGN_amusement_park "f"
-#define MGN_ATM "g"
-#define MGN_auto_repair "h"
-#define MGN_boating "I"
-#define MGN_camping "j"
-#define MGN_exit_ramp "k"
-#define MGN_first_aid "l"
-#define MGN_nav_aid "m"
-#define MGN_buoy "n"
-#define MGN_fuel "o"
-#define MGN_garden "p"
-#define MGN_golf "q"
-#define MGN_hotel "r"
-#define MGN_hunting_fishing "s"
-#define MGN_large_city "t"
-#define MGN_lighthouse "u"
-#define MGN_major_city "v"
-#define MGN_marina "w"
-#define MGN_medium_city "x"
-#define MGN_museum "y"
-#define MGN_obstruction "z"
-#define MGN_park "aa"
-#define MGN_resort "ab"
-#define MGN_restaurant "ac"
-#define MGN_rock "ad"
-#define MGN_scuba "ae"
-#define MGN_RV_service "af"
-#define MGN_shooting "ag"
-#define MGN_sight_seeing "ah"
-#define MGN_small_city "ai"
-#define MGN_sounding "aj"
-#define MGN_sports_arena "ak"
-#define MGN_tourist_info "al"
-#define MGN_truck_service "am"
-#define MGN_winery "an"
-#define MGN_wreck "ao"
-#define MGN_zoo "ap"
-
-
-/*
- * Mapping from APRS symbols to Magellan.
- *
- * This is a bit of a challenge because there 
- * are no icons for moving objects.
- * We can use airport for flying things but 
- * what about wheeled transportation devices?
- */
-
-// TODO:  NEEDS MORE WORK!!!
-
-
-#define MGN_default MGN_crossed_square
-
-#define SYMTAB_SIZE 95
-
-static const char mgn_primary_symtab[SYMTAB_SIZE][3] =  {
-
-	MGN_default,		//     00  	 --no-symbol--
-	MGN_default,		//  !  01  	 Police, Sheriff
-	MGN_default,		//  "  02  	 reserved  (was rain)
-	MGN_aerial,		//  #  03  	 DIGI (white center)
-	MGN_default,		//  $  04  	 PHONE
-	MGN_aerial,		//  %  05  	 DX CLUSTER
-	MGN_aerial,		//  &  06  	 HF GATEway
-	MGN_airport,		//  '  07  	 Small AIRCRAFT
-	MGN_aerial,		//  (  08  	 Mobile Satellite Station
-	MGN_default,		//  )  09  	 Wheelchair (handicapped)
-	MGN_default,		//  *  10  	 SnowMobile
-	MGN_default,		//  +  11  	 Red Cross
-	MGN_default,		//  ,  12  	 Boy Scouts
-	MGN_house,		//  -  13  	 House QTH (VHF)
-	MGN_default,		//  .  14  	 X
-	MGN_default,		//  /  15  	 Red Dot
-	MGN_default,		//  0  16  	 # circle (obsolete)
-	MGN_default,		//  1  17  	 TBD
-	MGN_default,		//  2  18  	 TBD
-	MGN_default,		//  3  19  	 TBD
-	MGN_default,		//  4  20  	 TBD
-	MGN_default,		//  5  21  	 TBD
-	MGN_default,		//  6  22  	 TBD
-	MGN_default,		//  7  23  	 TBD
-	MGN_default,		//  8  24  	 TBD
-	MGN_default,		//  9  25  	 TBD
-	MGN_default,		//  :  26  	 FIRE
-	MGN_camping,		//  ;  27  	 Campground (Portable ops)
-	MGN_default,		//  <  28  	 Motorcycle
-	MGN_default,		//  =  29  	 RAILROAD ENGINE
-	MGN_default,		//  >  30  	 CAR
-	MGN_default,		//  ?  31  	 SERVER for Files
-	MGN_default,		//  @  32  	 HC FUTURE predict (dot)
-	MGN_first_aid,		//  A  33  	 Aid Station
-	MGN_aerial,		//  B  34  	 BBS or PBBS
-	MGN_boating,		//  C  35  	 Canoe
-	MGN_default,		//  D  36  	 
-	MGN_default,		//  E  37  	 EYEBALL (Eye catcher!)
-	MGN_default,		//  F  38  	 Farm Vehicle (tractor)
-	MGN_default,		//  G  39  	 Grid Square (6 digit)
-	MGN_hotel,		//  H  40  	 HOTEL (blue bed symbol)
-	MGN_aerial,		//  I  41  	 TcpIp on air network stn
-	MGN_default,		//  J  42  	 
-	MGN_default,		//  K  43  	 School
-	MGN_default,		//  L  44  	 PC user
-	MGN_default,		//  M  45  	 MacAPRS
-	MGN_aerial,		//  N  46  	 NTS Station
-	MGN_airport,		//  O  47  	 BALLOON
-	MGN_default,		//  P  48  	 Police
-	MGN_default,		//  Q  49  	 TBD
-	MGN_RV_service,		//  R  50  	 REC. VEHICLE
-	MGN_airport,		//  S  51  	 SHUTTLE
-	MGN_default,		//  T  52  	 SSTV
-	MGN_default,		//  U  53  	 BUS
-	MGN_default,		//  V  54  	 ATV
-	MGN_default,		//  W  55  	 National WX Service Site
-	MGN_default,		//  X  56  	 HELO
-	MGN_boating,		//  Y  57  	 YACHT (sail)
-	MGN_default,		//  Z  58  	 WinAPRS
-	MGN_default,		//  [  59  	 Human/Person (HT)
-	MGN_default,		//  \  60  	 TRIANGLE(DF station)
-	MGN_default,		//  ]  61  	 MAIL/PostOffice(was PBBS)
-	MGN_airport,		//  ^  62  	 LARGE AIRCRAFT
-	MGN_default,		//  _  63  	 WEATHER Station (blue)
-	MGN_aerial,		//  `  64  	 Dish Antenna
-	MGN_default,		//  a  65  	 AMBULANCE
-	MGN_default,		//  b  66  	 BIKE
-	MGN_default,		//  c  67  	 Incident Command Post
-	MGN_default,		//  d  68  	 Fire dept
-	MGN_zoo,		//  e  69  	 HORSE (equestrian)
-	MGN_default,		//  f  70  	 FIRE TRUCK
-	MGN_airport,		//  g  71  	 Glider
-	MGN_default,		//  h  72  	 HOSPITAL
-	MGN_default,		//  i  73  	 IOTA (islands on the air)
-	MGN_default,		//  j  74  	 JEEP
-	MGN_default,		//  k  75  	 TRUCK
-	MGN_default,		//  l  76  	 Laptop
-	MGN_aerial,		//  m  77  	 Mic-E Repeater
-	MGN_default,		//  n  78  	 Node (black bulls-eye)
-	MGN_default,		//  o  79  	 EOC
-	MGN_zoo,		//  p  80  	 ROVER (puppy, or dog)
-	MGN_default,		//  q  81  	 GRID SQ shown above 128 m
-	MGN_aerial,		//  r  82  	 Repeater
-	MGN_default,		//  s  83  	 SHIP (pwr boat)
-	MGN_default,		//  t  84  	 TRUCK STOP
-	MGN_default,		//  u  85  	 TRUCK (18 wheeler)
-	MGN_default,		//  v  86  	 VAN
-	MGN_default,		//  w  87  	 WATER station
-	MGN_aerial,		//  x  88  	 xAPRS (Unix)
-	MGN_aerial,		//  y  89  	 YAGI @ QTH
-	MGN_default,		//  z  90  	 TBD
-	MGN_default,		//  {  91  	 
-	MGN_default,		//  |  92  	 TNC Stream Switch
-	MGN_default,		//  }  93  	 
-	MGN_default };		//  ~  94  	 TNC Stream Switch
-
-
-static const char mgn_alternate_symtab[SYMTAB_SIZE][3] =  {
-
-	MGN_default,		//     00  	 --no-symbol--
-	MGN_default,		//  !  01  	 EMERGENCY (!)
-	MGN_default,		//  "  02  	 reserved
-	MGN_aerial,		//  #  03  	 OVERLAY DIGI (green star)
-	MGN_ATM,		//  $  04  	 Bank or ATM  (green box)
-	MGN_default,		//  %  05  	 Power Plant with overlay
-	MGN_aerial,		//  &  06  	 I=Igte IGate R=RX T=1hopTX 2=2hopTX
-	MGN_default,		//  '  07  	 Crash (& now Incident sites)
-	MGN_default,		//  (  08  	 CLOUDY (other clouds w ovrly)
-	MGN_aerial,		//  )  09  	 Firenet MEO, MODIS Earth Obs.
-	MGN_default,		//  *  10  	 SNOW (& future ovrly codes)
-	MGN_default,		//  +  11  	 Church
-	MGN_default,		//  ,  12  	 Girl Scouts
-	MGN_house,		//  -  13  	 House (H=HF) (O = Op Present)
-	MGN_default,		//  .  14  	 Ambiguous (Big Question mark)
-	MGN_default,		//  /  15  	 Waypoint Destination
-	MGN_default,		//  0  16  	 CIRCLE (E/I/W=IRLP/Echolink/WIRES)
-	MGN_default,		//  1  17  	 
-	MGN_default,		//  2  18  	 
-	MGN_default,		//  3  19  	
-	MGN_default,		//  4  20  
-	MGN_default,		//  5  21 
-	MGN_default,		//  6  22
-	MGN_default,		//  7  23
-	MGN_aerial,		//  8  24  	 802.11 or other network node
-	MGN_fuel,		//  9  25  	 Gas Station (blue pump)
-	MGN_default,		//  :  26  	 Hail (& future ovrly codes)
-	MGN_park,		//  ;  27  	 Park/Picnic area
-	MGN_default,		//  <  28  	 ADVISORY (one WX flag)
-	MGN_default,		//  =  29  	 APRStt Touchtone (DTMF users)
-	MGN_default,		//  >  30  	 OVERLAID CAR
-	MGN_tourist_info,	//  ?  31  	 INFO Kiosk  (Blue box with ?)
-	MGN_default,		//  @  32  	 HURRICANE/Trop-Storm
-	MGN_box,		//  A  33  	 overlayBOX DTMF & RFID & XO
-	MGN_default,		//  B  34  	 Blwng Snow (& future codes)
-	MGN_boating,		//  C  35  	 Coast Guard
-	MGN_default,		//  D  36  	 Drizzle (proposed APRStt)
-	MGN_default,		//  E  37  	 Smoke (& other vis codes)
-	MGN_default,		//  F  38  	 Freezng rain (&future codes)
-	MGN_default,		//  G  39  	 Snow Shwr (& future ovrlys)
-	MGN_default,		//  H  40  	 Haze (& Overlay Hazards)
-	MGN_default,		//  I  41  	 Rain Shower
-	MGN_default,		//  J  42  	 Lightning (& future ovrlys)
-	MGN_default,		//  K  43  	 Kenwood HT (W)
-	MGN_lighthouse,		//  L  44  	 Lighthouse
-	MGN_default,		//  M  45  	 MARS (A=Army,N=Navy,F=AF)
-	MGN_buoy,		//  N  46  	 Navigation Buoy
-	MGN_airport,		//  O  47  	 Rocket
-	MGN_default,		//  P  48  	 Parking
-	MGN_default,		//  Q  49  	 QUAKE
-	MGN_restaurant,		//  R  50  	 Restaurant
-	MGN_aerial,		//  S  51  	 Satellite/Pacsat
-	MGN_default,		//  T  52  	 Thunderstorm
-	MGN_default,		//  U  53  	 SUNNY
-	MGN_nav_aid,		//  V  54  	 VORTAC Nav Aid
-	MGN_default,		//  W  55  	 # NWS site (NWS options)
-	MGN_default,		//  X  56  	 Pharmacy Rx (Apothicary)
-	MGN_aerial,		//  Y  57  	 Radios and devices
-	MGN_default,		//  Z  58  	 
-	MGN_default,		//  [  59  	 W.Cloud (& humans w Ovrly)
-	MGN_default,		//  \  60  	 New overlayable GPS symbol
-	MGN_default,		//  ]  61  	 
-	MGN_airport,		//  ^  62  	 # Aircraft (shows heading)
-	MGN_default,		//  _  63  	 # WX site (green digi)
-	MGN_default,		//  `  64  	 Rain (all types w ovrly)
-	MGN_aerial,		//  a  65  	 ARRL, ARES, WinLINK
-	MGN_default,		//  b  66  	 Blwng Dst/Snd (& others)
-	MGN_default,		//  c  67  	 CD triangle RACES/SATERN/etc
-	MGN_default,		//  d  68  	 DX spot by callsign
-	MGN_default,		//  e  69  	 Sleet (& future ovrly codes)
-	MGN_default,		//  f  70  	 Funnel Cloud
-	MGN_default,		//  g  71  	 Gale Flags
-	MGN_default,		//  h  72  	 Store. or HAMFST Hh=HAM store
-	MGN_box,		//  i  73  	 BOX or points of Interest
-	MGN_default,		//  j  74  	 WorkZone (Steam Shovel)
-	MGN_default,		//  k  75  	 Special Vehicle SUV,ATV,4x4
-	MGN_default,		//  l  76  	 Areas      (box,circles,etc)
-	MGN_default,		//  m  77  	 Value Sign (3 digit display)
-	MGN_default,		//  n  78  	 OVERLAY TRIANGLE
-	MGN_default,		//  o  79  	 small circle
-	MGN_default,		//  p  80  	 Prtly Cldy (& future ovrlys)
-	MGN_default,		//  q  81  	 
-	MGN_default,		//  r  82  	 Restrooms
-	MGN_default,		//  s  83  	 OVERLAY SHIP/boat (top view)
-	MGN_default,		//  t  84  	 Tornado
-	MGN_default,		//  u  85  	 OVERLAID TRUCK
-	MGN_default,		//  v  86  	 OVERLAID Van
-	MGN_default,		//  w  87  	 Flooding
-	MGN_wreck,		//  x  88  	 Wreck or Obstruction ->X<-
-	MGN_default,		//  y  89  	 Skywarn
-	MGN_default,		//  z  90  	 OVERLAID Shelter
-	MGN_default,		//  {  91  	 Fog (& future ovrly codes)
-	MGN_default,		//  |  92  	 TNC Stream Switch
-	MGN_default,		//  }  93  	 
-	MGN_default };		//  ~  94  	 TNC Stream Switch
-
diff --git a/mheard.h b/mheard.h
deleted file mode 100644
index f8466ba..0000000
--- a/mheard.h
+++ /dev/null
@@ -1,20 +0,0 @@
-
-
-/* mheard.h */
-
-#include "decode_aprs.h"	// for decode_aprs_t
-
-
-void mheard_init (int debug);
-
-void mheard_save_rf (int chan, decode_aprs_t *A, packet_t pp, alevel_t alevel, retry_t retries);
-
-void mheard_save_is (char *ptext);
-
-int mheard_count (int max_hops, int time_limit);
-
-int mheard_was_recently_nearby (char *role, char *callsign, int time_limit, int max_hops, double dlat, double dlon, double km);
-
-void mheard_set_msp (char *callsign, int num);
-
-int mheard_get_msp (char *callsign);
\ No newline at end of file
diff --git a/morse.h b/morse.h
deleted file mode 100644
index e34dd7b..0000000
--- a/morse.h
+++ /dev/null
@@ -1,8 +0,0 @@
-/* morse.h */
-
-int morse_init (struct audio_s *audio_config_p, int amp) ;
-
-int morse_send (int chan, char *str, int wpm, int txdelay, int txtail);
-
-#define MORSE_DEFAULT_WPM 10
-
diff --git a/multi_modem.h b/multi_modem.h
deleted file mode 100644
index de3061e..0000000
--- a/multi_modem.h
+++ /dev/null
@@ -1,24 +0,0 @@
-/* multi_modem.h */
-
-#ifndef MULTI_MODEM_H
-#define MULTI_MODEM 1
-
-/* Needed for typedef retry_t. */
-#include "hdlc_rec2.h"
-
-/* Needed for struct audio_s */
-#include "audio.h"
-
-
-void multi_modem_init (struct audio_s *pmodem); 
-
-void multi_modem_process_sample (int c, int audio_sample);
-
-int multi_modem_get_dc_average (int chan);
-
-// Deprecated.  Replace with ...packet
-void multi_modem_process_rec_frame (int chan, int subchan, int slice, unsigned char *fbuf, int flen, alevel_t alevel, retry_t retries, int is_fx25);
-
-void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, int is_fx25);
-
-#endif
diff --git a/pfilter.h b/pfilter.h
deleted file mode 100644
index d54e056..0000000
--- a/pfilter.h
+++ /dev/null
@@ -1,13 +0,0 @@
-
-/* pfilter.h */
-
-
-#include "igate.h"		// for igate_config_s
-
-
-
-void pfilter_init (struct igate_config_s *p_igate_config, int debug_level);
-
-int pfilter (int from_chan, int to_chan, char *filter, packet_t pp, int is_aprs);
-
-int is_telem_metadata (char *infop);
\ No newline at end of file
diff --git a/ptt.h b/ptt.h
deleted file mode 100644
index 6e75253..0000000
--- a/ptt.h
+++ /dev/null
@@ -1,26 +0,0 @@
-
-
-#ifndef PTT_H
-#define PTT_H 1
-
-
-#include "audio.h"	/* for struct audio_s and definitions for octype values */
-
-
-void ptt_set_debug(int debug);
-
-void ptt_init (struct audio_s *p_modem);
-
-void ptt_set (int octype, int chan, int ptt); 
-
-void ptt_term (void);
-
-int get_input (int it, int chan);
-
-#endif
-
-
-/* end ptt.h */
-
-
-
diff --git a/recv.h b/recv.h
deleted file mode 100644
index 3201991..0000000
--- a/recv.h
+++ /dev/null
@@ -1,6 +0,0 @@
-
-/* recv.h */
-
-void recv_init (struct audio_s *pa);
-
-void recv_process (void);
\ No newline at end of file
diff --git a/redecode.h b/redecode.h
deleted file mode 100644
index ffd9a95..0000000
--- a/redecode.h
+++ /dev/null
@@ -1,15 +0,0 @@
-
-
-#ifndef REDECODE_H
-#define REDECODE_H 1
-
-#include "rrbb.h"	
-
-
-extern void redecode_init (struct audio_s *p_audio_config);
-
-
-#endif
-
-/* end redecode.h */
-
diff --git a/release/moc_predefs.h b/release/moc_predefs.h
new file mode 100644
index 0000000..54e9037
--- /dev/null
+++ b/release/moc_predefs.h
@@ -0,0 +1,11 @@
+#define _MSC_EXTENSIONS 
+#define _INTEGRAL_MAX_BITS 64
+#define _MSC_VER 1916
+#define _MSC_FULL_VER 191627043
+#define _MSC_BUILD 0
+#define _WIN32 
+#define _M_IX86 600
+#define _M_IX86_FP 2
+#define _CPPRTTI 
+#define _MT 
+#define _DLL 
diff --git a/rpack.h b/rpack.h
deleted file mode 100644
index d972a54..0000000
--- a/rpack.h
+++ /dev/null
@@ -1,94 +0,0 @@
-
-/*------------------------------------------------------------------
- *
- * File:        rpack.h
- *
- * Purpose:   	Definition of Garmin Rino message format.
- *		
- * References:	http://www.radio-active.net.au/web3/APRS/Resources/RINO
- *
- *		http://www.radio-active.net.au/web3/APRS/Resources/RINO/OnAir
- *
- *---------------------------------------------------------------*/
-
-
-#ifndef RPACK_H
-#define RPACK_H 1
-
-
-#define RPACK_FRAME_LEN 168
-
-
-#ifdef RPACK_C		/* Expose private details */
-
-
- 
-// Transmission order is LSB first. 
-
-struct __attribute__((__packed__)) rpack_s {
-
-	int lat;		// Latitude.
-				// Signed integer.  Scaled by 2**30/90.
-
-	int lon;		// Longitude.  Same encoding.
-
-	char unknown1;		// Unproven theory: altitude.	
-	char unknown2;		
-
-	unsigned name0:6;	// 10 character name.
-	unsigned name1:6;	// Bit packing is implementation dependent.
-	unsigned name2:6;	// Should rewrite to be more portable.
-	unsigned name3:6;
-	unsigned name4:6;
-	unsigned name5:6;
-	unsigned name6:6;
-	unsigned name7:6;
-	unsigned name8:6;
-	unsigned name9:6;
-
-	unsigned symbol:5;	
-
-	unsigned unknown3:7;		
-				
-	
-//	unsigned crc:16;	// Safe bet this is CRC for error checking.
-
-	unsigned char crc1;
-	unsigned char crc2;
-
-	char dummy[3];		// Total size should be 24 bytes if no gaps.
-
-};
-
-#else			/* Show only public interface.  */
-
-
-struct rpack_s {
-	char stuff[24];
-};
-
-
-#endif
-
-
-
-void rpack_set_bit (struct rpack_s *rp, int position, int value);
-
-int rpack_is_valid (struct rpack_s *rp);
-
-int rpack_get_bit (struct rpack_s *rp, int position);
-
-double rpack_get_lat (struct rpack_s *rp);
-
-double rpack_get_lon (struct rpack_s *rp);
-
-int rpack_get_symbol (struct rpack_s *rp);
-
-void rpack_get_name (struct rpack_s *rp, char *str);
-
-
-
-#endif
-
-/* end rpack.h */
-	
diff --git a/rrbb.h b/rrbb.h
deleted file mode 100644
index 4b28372..0000000
--- a/rrbb.h
+++ /dev/null
@@ -1,92 +0,0 @@
-
-#ifndef RRBB_H
-
-#define RRBB_H
-
-
-#define FASTER13 1		// Don't pack 8 samples per byte.
-
-
-//typedef short slice_t;
-
-
-/* 
- * Maximum size (in bytes) of an AX.25 frame including the 2 octet FCS. 
- */
-
-#define MAX_FRAME_LEN ((AX25_MAX_PACKET_LEN) + 2)	
-
-/*
- * Maximum number of bits in AX.25 frame excluding the flags.
- * Adequate for extreme case of bit stuffing after every 5 bits
- * which could never happen.
- */
-
-#define MAX_NUM_BITS (MAX_FRAME_LEN * 8 * 6 / 5)
-
-typedef struct rrbb_s {
-	int magic1;
-	struct rrbb_s* nextp;	/* Next pointer to maintain a queue. */
-
-	int chan;		/* Radio channel from which it was received. */
-	int subchan;		/* Which modem when more than one per channel. */
-	int slice;		/* Which slicer. */
-
-	alevel_t alevel;	/* Received audio level at time of frame capture. */
-	unsigned int len;	/* Current number of samples in array. */
-
-	int is_scrambled;	/* Is data scrambled G3RUH / K9NG style? */
-	int descram_state;	/* Descrambler state before first data bit of frame. */
-	int prev_descram;	/* Previous descrambled bit. */
-
-	unsigned char fdata[MAX_NUM_BITS];
-
-	int magic2;
-} *rrbb_t;
-
-
-
-rrbb_t rrbb_new (int chan, int subchan, int slice, int is_scrambled, int descram_state, int prev_descram);
-
-void rrbb_clear (rrbb_t b, int is_scrambled, int descram_state, int prev_descram);
-
-
-static inline /*__attribute__((always_inline))*/ void rrbb_append_bit (rrbb_t b, const unsigned char val)
-{
-	if (b->len >= MAX_NUM_BITS) {
-	  return;	/* Silently discard if full. */
-	}
-	b->fdata[b->len] = val;
-	b->len++;
-}
-
-static inline /*__attribute__((always_inline))*/ unsigned char rrbb_get_bit (const rrbb_t b, const int ind)
-{
-	return (b->fdata[ind]);
-}
-
-
-void rrbb_chop8 (rrbb_t b);
-
-int rrbb_get_len (rrbb_t b);
-
-//void rrbb_flip_bit (rrbb_t b, unsigned int ind);
-
-void rrbb_delete (rrbb_t b);
-
-void rrbb_set_nextp (rrbb_t b, rrbb_t np);
-rrbb_t rrbb_get_nextp (rrbb_t b);
-
-int rrbb_get_chan (rrbb_t b);
-int rrbb_get_subchan (rrbb_t b);
-int rrbb_get_slice (rrbb_t b);
-
-void rrbb_set_audio_level (rrbb_t b, alevel_t alevel);
-alevel_t rrbb_get_audio_level (rrbb_t b);
-
-int rrbb_get_is_scrambled (rrbb_t b);
-int rrbb_get_descram_state (rrbb_t b);
-int rrbb_get_prev_descram (rrbb_t b);
-
-
-#endif
diff --git a/serial_port.h b/serial_port.h
deleted file mode 100644
index 8a65a0b..0000000
--- a/serial_port.h
+++ /dev/null
@@ -1,32 +0,0 @@
-/* serial_port.h */
-
-
-#ifndef SERIAL_PORT_H
-#define SERIAL_PORT_H 1
-
-
-#if __WIN32__
-
-#include <stdlib.h>
-
-typedef HANDLE MYFDTYPE;
-#define MYFDERROR INVALID_HANDLE_VALUE
-
-#else
-
-typedef int MYFDTYPE;
-#define MYFDERROR (-1)
-
-#endif
-
-
-extern MYFDTYPE serial_port_open (char *devicename, int baud);
-
-extern int serial_port_write (MYFDTYPE fd, char *str, int len);
-
-extern int serial_port_get1 (MYFDTYPE fd);
-
-extern void serial_port_close (MYFDTYPE fd);
-
-
-#endif
\ No newline at end of file
diff --git a/server.h b/server.h
deleted file mode 100644
index 4cc2ea0..0000000
--- a/server.h
+++ /dev/null
@@ -1,32 +0,0 @@
-
-/* 
- * Name:	server.h
- */
-
-
-#include "ax25_pad.h"		/* for packet_t */
-
-#include "config.h"
-
-
-void server_set_debug (int n);
-
-void server_init (struct audio_s *audio_config_p, struct misc_config_s *misc_config);
-
-void server_send_rec_packet (int chan, packet_t pp, unsigned char *fbuf,  int flen);
-
-void server_send_monitored (int chan, packet_t pp, int own_xmit);
-
-int server_callsign_registered_by_client (char *callsign);
-
-
-void server_link_established (int chan, int client, char *remote_call, char *own_call, int incoming);
-
-void server_link_terminated (int chan, int client, char *remote_call, char *own_call, int timeout);
-
-void server_rec_conn_data (int chan, int client, char *remote_call, char *own_call, int pid, char *data_ptr, int data_len);
-
-void server_outstanding_frames_reply (int chan, int client, char *own_call, char *remote_call, int count);
-
-
-/* end server.h */
diff --git a/sm_main.c b/sm_main.c
index ed54f92..d2c6cfd 100644
--- a/sm_main.c
+++ b/sm_main.c
@@ -27,7 +27,6 @@ void make_core_BPF(UCHAR snd_ch, short freq, short width);
 void make_core_TXBPF(UCHAR snd_ch, float freq, float width);
 void make_core_INTR(UCHAR snd_ch);
 void make_core_LPF(UCHAR snd_ch, short width);
-void wf_pointer(int snd_ch);
 void dw9600ProcessSample(int snd_ch, short Sample);
 void init_RUH48(int snd_ch);
 void init_RUH96(int snd_ch);
@@ -725,7 +724,7 @@ void init_speed(int snd_ch)
 	  form1.show_freq_a;
 	  form1.show_freq_b;
 	  */
-	wf_pointer(snd_ch);
+	NeedWaterfallHeaders = TRUE;
 
 	CheckPSKWindows();
 }
@@ -1065,7 +1064,6 @@ void BufferFull(short * Samples, int nSamples)			// These are Stereo Samples
 
 		Toggle++;
 
-
 		Needed = FFTSize - fftCount;
 
 		if (Needed <= rx_bufsize)
@@ -1080,7 +1078,6 @@ void BufferFull(short * Samples, int nSamples)			// These are Stereo Samples
 
 			if ((Toggle & 1) || (UsingBothChannels == 0))
 				doWaterfall(FirstWaterfallChan);
-	
 
 			if (data2)
 			{
@@ -1093,6 +1090,9 @@ void BufferFull(short * Samples, int nSamples)			// These are Stereo Samples
 					doWaterfall(1);
 			}
 
+			if (Firstwaterfall || Secondwaterfall)
+				displayWaterfall();
+
 			remainingSamples = rx_bufsize - Needed;
 			fftCount = 0;
 
diff --git a/symbols.h b/symbols.h
deleted file mode 100644
index 5ed91ad..0000000
--- a/symbols.h
+++ /dev/null
@@ -1,19 +0,0 @@
-
-/* symbols.h */
-
-void symbols_init (void);
-
-void symbols_list (void);
-
-void symbols_from_dest_or_src (char dti, char *src, char *dest, char *symtab, char *symbol);
-
-int symbols_into_dest (char symtab, char symbol, char *dest);
-
-void symbols_get_description (char symtab, char symbol, char *description, size_t desc_size);
-
-int symbols_code_from_description (char overlay, char *description, char *symtab, char *symbol);
-
-void symbols_to_tones (char symtab, char symbol, char *tones, size_t tonessize);
-
-
-/* end symbols.h */
diff --git a/telemetry.h b/telemetry.h
deleted file mode 100644
index 4ef9b62..0000000
--- a/telemetry.h
+++ /dev/null
@@ -1,15 +0,0 @@
-
-
-/* telemetry.h */
-
-void telemetry_data_original (char *station, char *info, int quiet, char *output, size_t outputsize, char *comment, size_t commentsize);
- 
-void telemetry_data_base91 (char *station, char *cdata, char *output, size_t outputsize);
- 
-void telemetry_name_message (char *station, char *msg);
- 
-void telemetry_unit_label_message (char *station, char *msg);
-
-void telemetry_coefficents_message (char *station, char *msg, int quiet);
-
-void telemetry_bit_sense_message (char *station, char *msg, int quiet);
diff --git a/tq.h b/tq.h
deleted file mode 100644
index 37599d5..0000000
--- a/tq.h
+++ /dev/null
@@ -1,41 +0,0 @@
-
-/*------------------------------------------------------------------
- *
- * Module:      tq.h
- *
- * Purpose:   	Transmit queue - hold packets for transmission until the channel is clear.
- *		
- *---------------------------------------------------------------*/
-
-#ifndef TQ_H
-#define TQ_H 1
-
-#include "ax25_pad.h"
-#include "audio.h"
-
-#define TQ_NUM_PRIO 2				/* Number of priorities. */
-
-#define TQ_PRIO_0_HI 0
-#define TQ_PRIO_1_LO 1
-
-
-
-void tq_init (struct audio_s *audio_config_p);
-
-void tq_append (int chan, int prio, packet_t pp);
-
-void lm_data_request (int chan, int prio, packet_t pp);
-
-void lm_seize_request (int chan);
-
-void tq_wait_while_empty (int chan);
-
-packet_t tq_remove (int chan, int prio);
-
-packet_t tq_peek (int chan, int prio);
-
-int tq_count (int chan, int prio, char *source, char *dest, int bytes);
-
-#endif
-
-/* end tq.h */
diff --git a/tt_text.h b/tt_text.h
deleted file mode 100644
index 7cab3b8..0000000
--- a/tt_text.h
+++ /dev/null
@@ -1,38 +0,0 @@
-
-/* tt_text.h */
-
-
-/* Encode normal human readable to DTMF representation. */
-
-int tt_text_to_multipress (const char *text, int quiet, char *buttons);
-
-int tt_text_to_two_key (const char *text, int quiet, char *buttons);
-
-int tt_text_to_call10 (const char *text, int quiet, char *buttons);
-
-int tt_text_to_mhead (const char *text, int quiet, char *buttons, size_t buttonsiz);
-
-int tt_text_to_satsq (const char *text, int quiet, char *buttons, size_t buttonsiz);
-
-int tt_text_to_ascii2d (const char *text, int quiet, char *buttons);
-
-
-/* Decode DTMF to normal human readable form. */
-
-int tt_multipress_to_text (const char *buttons, int quiet, char *text);
-
-int tt_two_key_to_text (const char *buttons, int quiet, char *text);
-
-int tt_call10_to_text (const char *buttons, int quiet, char *text);
-
-int tt_call5_suffix_to_text (const char *buttons, int quiet, char *text);
-
-int tt_mhead_to_text (const char *buttons, int quiet, char *text, size_t textsiz);
-
-int tt_satsq_to_text (const char *buttons, int quiet, char *text);
-
-int tt_ascii2d_to_text (const char *buttons, int quiet, char *text);
-
-
-
-/* end tt_text.h */
\ No newline at end of file
diff --git a/tt_user.h b/tt_user.h
deleted file mode 100644
index 4ff2ec8..0000000
--- a/tt_user.h
+++ /dev/null
@@ -1,15 +0,0 @@
-
-/* tt_user.h */
-
-
-#include "audio.h"
-
-void tt_user_init (struct audio_s *p_audio_config, struct tt_config_s *p);
-
-int tt_user_heard (char *callsign, int ssid, char overlay, char symbol, char *loc_text, double latitude, 
-		double longitude, int ambiguity, char *freq, char *ctcss, char *comment, char mic_e, char *dao);
-
-int tt_3char_suffix_search (char *suffix, char *callsign);
-
-void tt_user_background (void);
-void tt_user_dump (void);
\ No newline at end of file
diff --git a/tune.h b/tune.h
deleted file mode 100644
index 8d1c8b6..0000000
--- a/tune.h
+++ /dev/null
@@ -1 +0,0 @@
- 
diff --git a/version.h b/version.h
deleted file mode 100644
index a09490c..0000000
--- a/version.h
+++ /dev/null
@@ -1,21 +0,0 @@
-
-/* Dire Wolf version 1.6 */
-
-// Put in destination field to identify the equipment used.
-
-#define APP_TOCALL "APDW"		// Assigned by WB4APR in tocalls.txt
-
-// This now comes from compile command line options.
-
-//#define MAJOR_VERSION 1
-//#define MINOR_VERSION 6
-//#define EXTRA_VERSION "Beta Test"
-
-
-// For user-defined data format.
-// APRS protocol spec Chapter 18 and http://www.aprs.org/aprs11/expfmts.txt
-
-#define USER_DEF_USER_ID 'D'		// user id D for direwolf
-
-#define USER_DEF_TYPE_AIS 'A'		// data type A for AIS NMEA sentence
-#define USER_DEF_TYPE_EAS 'E'		// data type E for EAS broadcasts
diff --git a/waypoint.h b/waypoint.h
deleted file mode 100644
index 3ba6f1c..0000000
--- a/waypoint.h
+++ /dev/null
@@ -1,24 +0,0 @@
-
-/* 
- * Name:	waypoint.h
- */
-
-
-#include "ax25_pad.h"		/* for packet_t */
-
-#include "config.h"		/* for struct misc_config_s */
-
-
-void waypoint_init (struct misc_config_s *misc_config);
-
-void waypoint_set_debug (int n);
-
-void waypoint_send_sentence (char *wname_in, double dlat, double dlong, char symtab, char symbol, 
-			float alt, float course, float speed, char *comment_in);
-
-void waypoint_send_ais (char *sentence);
-
-void waypoint_term ();
-
-
-/* end waypoint.h */
diff --git a/xid.h b/xid.h
deleted file mode 100644
index a221b73..0000000
--- a/xid.h
+++ /dev/null
@@ -1,32 +0,0 @@
-
-
-/* xid.h */
-
-
-#include "ax25_pad.h"		// for enum ax25_modulo_e
-
-
-struct xid_param_s {
-
-	int full_duplex;
-	
-	// Order is important because negotiation keeps the lower value of
-	// REJ  (srej_none),  SREJ (default without negotiation), Multi-SREJ (if both agree).
-
-	enum srej_e { srej_none=0, srej_single=1, srej_multi=2, srej_not_specified=3 } srej;
-
-	enum ax25_modulo_e modulo;
-
-	int i_field_length_rx;	/* In bytes.  XID has it in bits. */
-
-	int window_size_rx;
-
-	int ack_timer;		/* "T1" in mSec. */
-
-	int retries;		/* "N1" */
-};
-
-
-int xid_parse (unsigned char *info, int info_len, struct xid_param_s *result, char *desc, int desc_size);
-
-int xid_encode (struct xid_param_s *param, unsigned char *info, cmdres_t cr);
\ No newline at end of file
diff --git a/xmit.h b/xmit.h
deleted file mode 100644
index 248037d..0000000
--- a/xmit.h
+++ /dev/null
@@ -1,27 +0,0 @@
-
-
-#ifndef XMIT_H
-#define XMIT_H 1
-
-#include "audio.h"	/* for struct audio_s */
-
-
-extern void xmit_init (struct audio_s *p_modem, int debug_xmit_packet);
-
-extern void xmit_set_txdelay (int channel, int value);
-
-extern void xmit_set_persist (int channel, int value);
-
-extern void xmit_set_slottime (int channel, int value);
-
-extern void xmit_set_txtail (int channel, int value);
-
-extern void xmit_set_fulldup (int channel, int value);
-
-
-extern int xmit_speak_it (char *script, int c, char *msg);
-
-#endif
-
-/* end xmit.h */
-