diff --git a/ChanSort.Api/ChanSort.Api.csproj b/ChanSort.Api/ChanSort.Api.csproj index b6b6db8..91d5038 100644 --- a/ChanSort.Api/ChanSort.Api.csproj +++ b/ChanSort.Api/ChanSort.Api.csproj @@ -82,11 +82,11 @@ True Resources.resx - + - + diff --git a/ChanSort.Api/Controller/Editor.cs b/ChanSort.Api/Controller/Editor.cs index c9143b5..326a68d 100644 --- a/ChanSort.Api/Controller/Editor.cs +++ b/ChanSort.Api/Controller/Editor.cs @@ -7,6 +7,7 @@ namespace ChanSort.Api { public DataRoot DataRoot; public ChannelList ChannelList; + private UnsortedChannelMode unsortedChannelMode; #if false #region LoadDvbViewerFiles() @@ -272,5 +273,71 @@ namespace ChanSort.Api } } #endregion + + + #region AutoNumberingForUnassignedChannels() + + public void AutoNumberingForUnassignedChannels(UnsortedChannelMode mode) + { + this.unsortedChannelMode = mode; + foreach (var list in DataRoot.ChannelLists) + { + var sortedChannels = list.Channels.OrderBy(ChanSortCriteria).ToList(); + int maxProgNr = 0; + + foreach (var appChannel in sortedChannels) + { + if (appChannel.RecordIndex < 0) + continue; + + if (appChannel.NewProgramNr <= 0 && mode == UnsortedChannelMode.Hide) + continue; + + int progNr = GetNewProgramNr(appChannel, ref maxProgNr); + appChannel.NewProgramNr = progNr; + } + } + } + + #region ChanSortCriteria() + private string ChanSortCriteria(ChannelInfo channel) + { + // explicitly sorted + if (channel.NewProgramNr != 0) + return channel.NewProgramNr.ToString("d4"); + + // eventually hide unsorted channels + if (this.unsortedChannelMode == UnsortedChannelMode.Hide) + return "Z"; + + // eventually append in old order + if (this.unsortedChannelMode == UnsortedChannelMode.AppendInOrder) + return "B" + channel.OldProgramNr.ToString("d4"); + + // sort alphabetically, with "." and "" on the bottom + if (channel.Name == ".") + return "B"; + if (channel.Name == "") + return "C"; + return "A" + channel.Name; + } + #endregion + + #region GetNewProgramNr() + private int GetNewProgramNr(ChannelInfo appChannel, ref int maxPrNr) + { + int prNr = appChannel.NewProgramNr; + if (prNr > maxPrNr) + maxPrNr = prNr; + if (prNr == 0) + { + if (appChannel.OldProgramNr != 0 && this.unsortedChannelMode != UnsortedChannelMode.Hide) + prNr = ++maxPrNr; + } + return prNr; + } + #endregion + + #endregion } } diff --git a/ChanSort.Api/Controller/SerializerBase.cs b/ChanSort.Api/Controller/SerializerBase.cs index 5d9f28e..3786114 100644 --- a/ChanSort.Api/Controller/SerializerBase.cs +++ b/ChanSort.Api/Controller/SerializerBase.cs @@ -4,13 +4,24 @@ namespace ChanSort.Api { public abstract class SerializerBase { + public class SupportedFeatures + { + public bool EraseChannelData { get; set; } + public bool ChannelNameEdit { get; set; } + public bool FileInformation { get; set; } + + public bool DeviceSettings { get; set; } + } + private Encoding defaultEncoding; public string FileName { get; set; } public DataRoot DataRoot { get; protected set; } + public SupportedFeatures Features { get; private set; } protected SerializerBase(string inputFile) { + this.Features = new SupportedFeatures(); this.FileName = inputFile; this.DataRoot = new DataRoot(); this.defaultEncoding = Encoding.GetEncoding("iso-8859-9"); @@ -18,7 +29,7 @@ namespace ChanSort.Api public abstract string DisplayName { get; } public abstract void Load(); - public abstract void Save(string tvOutputFile, string csvOutputFile, UnsortedChannelMode unsortedChannelMode); + public abstract void Save(string tvOutputFile, string csvOutputFile); public virtual Encoding DefaultEncoding { @@ -26,13 +37,10 @@ namespace ChanSort.Api set { this.defaultEncoding = value; } } - public bool SupportsEraseChannelData { get; protected set; } public virtual void EraseChannelData() { } public virtual string GetFileInformation() { return ""; } public virtual void ShowDeviceSettingsForm(object parentWindow) { } - - public bool SupportsChannelNameEdit { get; protected set; } } } diff --git a/ChanSort.Api/Lookup.csv b/ChanSort.Api/Lookup.csv index 265cf15..ed09645 100644 --- a/ChanSort.Api/Lookup.csv +++ b/ChanSort.Api/Lookup.csv @@ -420,57 +420,6 @@ TRANSP;120;12728 SERVICETYPE;Number;Description SERVICETYPE;01;SD-TV SERVICETYPE;02;Radio -SERVICETYPE;12;Daten/Test +SERVICETYPE;12;Data/Test SERVICETYPE;25;HD-TV -SERVICETYPE;211;Sky Select - -DVBT;Channel;MHz -DVBT;21;474 -DVBT;22;482 -DVBT;23;490 -DVBT;24;498 -DVBT;25;506 -DVBT;26;514 -DVBT;27;522 -DVBT;28;530 -DVBT;29;538 -DVBT;30;546 -DVBT;31;554 -DVBT;32;562 -DVBT;33;570 -DVBT;34;578 -DVBT;35;586 -DVBT;36;594 -DVBT;37;602 -DVBT;38;610 -DVBT;39;618 -DVBT;40;626 -DVBT;41;634 -DVBT;42;642 -DVBT;43;650 -DVBT;44;658 -DVBT;45;666 -DVBT;46;674 -DVBT;47;682 -DVBT;48;690 -DVBT;49;698 -DVBT;50;706 -DVBT;51;714 -DVBT;52;722 -DVBT;53;730 -DVBT;54;738 -DVBT;55;746 -DVBT;56;754 -DVBT;57;762 -DVBT;58;770 -DVBT;59;778 -DVBT;60;786 -DVBT;61;794 -DVBT;62;802 -DVBT;63;810 -DVBT;64;818 -DVBT;65;826 -DVBT;66;834 -DVBT;67;842 -DVBT;68;850 -DVBT;69;858 +SERVICETYPE;211;Option diff --git a/ChanSort.Api/Model/ChannelInfo.cs b/ChanSort.Api/Model/ChannelInfo.cs index 02eeba4..0bd59dd 100644 --- a/ChanSort.Api/Model/ChannelInfo.cs +++ b/ChanSort.Api/Model/ChannelInfo.cs @@ -11,8 +11,9 @@ namespace ChanSort.Api /// public readonly List Duplicates = new List(); - public SignalSource SignalSource { get; private set; } - public SignalType SignalType { get; private set; } + public virtual bool IsDeleted { get; set; } + public SignalSource SignalSource { get; protected set; } + public SignalType SignalType { get; protected set; } public int RecordIndex { get; set; } public int RecordOrder { get; set; } public int OldProgramNr { get; set; } @@ -42,6 +43,10 @@ namespace ChanSort.Api public bool IsNameModified { get; set; } #region ctor() + protected ChannelInfo() + { + } + /// /// Constructor for exiting TV channel /// @@ -201,5 +206,13 @@ namespace ChanSort.Api this.AddDebug(ptr[i]); } #endregion + + public virtual void UpdateRawData() + { + } + + public virtual void ChangeEncoding(System.Text.Encoding encoding) + { + } } } diff --git a/ChanSort.Api/Model/DataRoot.cs b/ChanSort.Api/Model/DataRoot.cs index 36a3a32..e55c0dd 100644 --- a/ChanSort.Api/Model/DataRoot.cs +++ b/ChanSort.Api/Model/DataRoot.cs @@ -74,7 +74,8 @@ namespace ChanSort.Api return list; } ChannelList newList = new ChannelList(signalSource, signalType); - this.AddChannelList(newList); + if (createIfNotExists) + this.AddChannelList(newList); return newList; } #endregion diff --git a/ChanSort.Api/Model/LookupData.cs b/ChanSort.Api/Model/LookupData.cs index e12ee80..93e0a3c 100644 --- a/ChanSort.Api/Model/LookupData.cs +++ b/ChanSort.Api/Model/LookupData.cs @@ -46,13 +46,6 @@ namespace ChanSort.Api } #endregion - #region GetDvbtTransponderFrequency() - public int GetDvbtTransponderFrequency(int transponderNr) - { - return this.dvbtFreqInMhzByTransponder.TryGet(transponderNr); - } - #endregion - #region GetServiceTypeDescription() public string GetServiceTypeDescription(int serviceType) { diff --git a/ChanSort.Api/Utils/Crc32.cs b/ChanSort.Api/Utils/Crc32.cs index 43ae1c9..e716e24 100644 --- a/ChanSort.Api/Utils/Crc32.cs +++ b/ChanSort.Api/Utils/Crc32.cs @@ -34,11 +34,11 @@ #endregion #region CalcCrc32() - public static unsafe uint CalcCrc32(byte* block, int length) + public static uint CalcCrc32(byte[] block, int start, int length) { uint crc32 = CrcMask; for (int i = 0; i < length; i++) - crc32 = crc32Table[(crc32 & 0xff) ^ block[i]] ^ (crc32 >> 8); + crc32 = crc32Table[(crc32 & 0xff) ^ block[start + i]] ^ (crc32 >> 8); return crc32; } #endregion diff --git a/ChanSort.Api/Utils/DataMapping.cs b/ChanSort.Api/Utils/DataMapping.cs index 87786f1..b33ee77 100644 --- a/ChanSort.Api/Utils/DataMapping.cs +++ b/ChanSort.Api/Utils/DataMapping.cs @@ -1,202 +1,194 @@ -using System.Text; +using System; +using System.Text; namespace ChanSort.Api { - public unsafe class DataMapping + public class DataMapping { - protected readonly Encoding stringEncoding; protected readonly IniFile.Section settings; - protected readonly int length; + private int baseOffset; + private byte[] data { get; set; } + public Encoding DefaultEncoding { get; set; } #region ctor() - public DataMapping(IniFile.Section settings, int structureLength, Encoding stringEncoding) + public DataMapping(IniFile.Section settings) { this.settings = settings; - this.length = structureLength; - this.stringEncoding = stringEncoding; + this.DefaultEncoding = Encoding.Default; } #endregion - #region DataPtr - public byte* DataPtr { get; set; } - #endregion - - #region DataLength - public int DataLength { get { return this.length; } } - #endregion - - #region Next() - public void Next() + #region SetDataPtr(), Data, BaseOffset + public void SetDataPtr(byte[] data, int baseOffset) { - this.DataPtr += this.length; + this.data = data; + this.baseOffset = baseOffset; } + + public byte[] Data { get { return this.data; } } + public int BaseOffset { get { return this.baseOffset; } set { this.baseOffset = value; } } #endregion + #region GetOffsets() - protected int[] GetOffsets(string key) + public int[] GetOffsets(string key) { return settings.GetIntList(key); } #endregion + public IniFile.Section Settings { get { return this.settings; } } - #region GetByte() - public byte GetByte(int off) - { - return off < 0 ? (byte)0 : this.DataPtr[off]; - } + #region Byte public byte GetByte(string key) { var offsets = settings.GetIntList(key); - return offsets.Length > 0 ? this.GetByte(offsets[0]) : (byte)0; + if (offsets.Length==0) return 0; + return this.data[baseOffset + offsets[0]]; + } + + public void SetByte(string key, int value) + { + var offsets = settings.GetIntList(key); + foreach (int offset in offsets) + this.data[baseOffset + offset] = (byte)value; } #endregion - #region GetWord() - public ushort GetWord(int off) - { - return off < 0 ? (ushort)0 : *(ushort*) (this.DataPtr + off); - } - + #region Word public ushort GetWord(string key) { var offsets = settings.GetIntList(key); - return offsets.Length > 0 ? this.GetWord(offsets[0]) : (ushort)0; - } - #endregion - - #region GetDword() - public uint GetDword(int off) - { - return off < 0 ? 0 : *(uint*) (this.DataPtr + off); - } - - public uint GetDword(string key) - { - var offsets = settings.GetIntList(key); - return offsets.Length > 0 ? this.GetDword(offsets[0]) : 0; - } - #endregion - - #region GetFloat() - public float GetFloat(int off) - { - return off < 0 ? 0 : *(float*) (this.DataPtr + off); - } - - public float GetFloat(string key) - { - var offsets = settings.GetIntList(key); - return offsets.Length > 0 ? this.GetFloat(offsets[0]) : 0; - } - #endregion - - #region GetFlag() - public bool GetFlag(int offset, byte mask) - { - return offset >= 0 && (this.GetByte(offset) & mask) != 0; - } - - public bool GetFlag(string valueKey, string maskKey) - { - byte mask = (byte)settings.GetInt(maskKey); - var offsets = settings.GetIntList(valueKey); - return offsets.Length > 0 && this.GetFlag(offsets[0], mask); - } - #endregion - - #region GetString() - public string GetString(int offset, int maxByteLen) - { - if (offset < 0) return null; - byte[] buffer = new byte[maxByteLen]; - for (int i = 0; i < maxByteLen; i++) - buffer[i] = this.DataPtr[offset + i]; - return stringEncoding.GetString(buffer).TrimEnd('\0'); - } - - public string GetString(string key, int maxLen) - { - var offsets = settings.GetIntList(key); - return offsets.Length == 0 ? null : GetString(offsets[0], maxLen); - } - #endregion - - - #region SetByte() - public void SetByte(int off, byte value) - { - if (off >= 0) - this.DataPtr[off] = value; - } - - public void SetByte(string key, byte value) - { - var offsets = settings.GetIntList(key); - foreach(int offset in offsets) - this.SetByte(offset, value); - } - #endregion - - #region SetWord() - public void SetWord(int off, int value) - { - if (off >= 0) - *(ushort*) (this.DataPtr + off) = (ushort)value; + if (offsets.Length == 0) return 0; + return BitConverter.ToUInt16(this.data, baseOffset + offsets[0]); } public void SetWord(string key, int value) { var offsets = settings.GetIntList(key); foreach (int offset in offsets) - this.SetWord(offset, value); + { + this.data[baseOffset + offset + 0] = (byte)value; + this.data[baseOffset + offset + 1] = (byte)(value>>8); + } } #endregion - #region SetDword() - public void SetDword(int off, uint value) + #region DWord + public long GetDword(string key) { - if (off >= 0) - *(uint*) (this.DataPtr + off) = value; + var offsets = settings.GetIntList(key); + if (offsets.Length == 0) return 0; + return BitConverter.ToUInt32(this.data, baseOffset + offsets[0]); } - public void SetDword(string key, uint value) + public void SetDword(string key, long value) { var offsets = settings.GetIntList(key); foreach (int offset in offsets) - this.SetDword(offset, value); + { + this.data[baseOffset + offset + 0] = (byte)value; + this.data[baseOffset + offset + 1] = (byte)(value >> 8); + this.data[baseOffset + offset + 2] = (byte)(value >> 16); + this.data[baseOffset + offset + 3] = (byte)(value >> 24); + } } #endregion - #region SetFloat() - public void SetFloat(int off, float value) + #region Float + public float GetFloat(string key) { - if (off >= 0) - *(float*)(this.DataPtr + off) = value; + var offsets = settings.GetIntList(key); + if (offsets.Length == 0) return 0; + return BitConverter.ToSingle(this.data, baseOffset + offsets[0]); } public void SetFloat(string key, float value) { var offsets = settings.GetIntList(key); + var bytes = BitConverter.GetBytes(value); foreach (int offset in offsets) - this.SetFloat(offset, value); + { + for (int i = 0; i < 4; i++) + this.data[baseOffset + offset + i] = bytes[i]; + } + } + #endregion + + #region GetFlag + + public bool GetFlag(string key) + { + return GetFlag("off" + key, "mask" + key); + } + + public bool GetFlag(string valueKey, string maskKey) + { + int mask = settings.GetInt(maskKey); + return GetFlag(valueKey, mask); + } + + public bool GetFlag(string valueKey, int mask) + { + if (mask == 0) return false; + var offsets = settings.GetIntList(valueKey); + if (offsets.Length == 0) return false; + return (this.data[baseOffset + offsets[0]] & mask) == mask; } #endregion #region SetFlag() - public void SetFlag(int offset, byte mask, bool set) + public void SetFlag(string key, bool value) { - byte val = this.GetByte(offset); - this.SetByte(offset, (byte)(set ? val | mask : val & ~mask)); + this.SetFlag("off" + key, "mask" + key, value); } - public void SetFlag(string valueKey, string maskKey, bool set) + public void SetFlag(string valueKey, string maskKey, bool value) { - byte mask = (byte)settings.GetInt(maskKey); + int mask = settings.GetInt(maskKey); + SetFlag(valueKey, mask, value); + } + + public void SetFlag(string valueKey, int mask, bool value) + { + if (mask == 0) return; var offsets = settings.GetIntList(valueKey); - foreach (int offset in offsets) - this.SetFlag(offset, mask, set); + foreach (var offset in offsets) + { + if (value) + this.data[baseOffset + offset] |= (byte)mask; + else + this.data[baseOffset + offset] &= (byte)~mask; + } + } + #endregion + + + #region GetString() + public string GetString(string key, int maxLen) + { + var offsets = settings.GetIntList(key); + if (offsets.Length == 0) return null; + int length = this.GetByte(key + "Length"); + if (length == 0) + length = maxLen; + var encoding = this.DefaultEncoding; + return encoding.GetString(this.data, baseOffset + offsets[0], length).TrimEnd('\0'); + } + #endregion + + #region SetString() + public void SetString(string key, string text, int maxLen) + { + var bytes = this.DefaultEncoding.GetBytes(text); + int len = Math.Min(bytes.Length, maxLen); + foreach (var offset in settings.GetIntList(key)) + { + Array.Copy(bytes, 0, this.data, baseOffset + offset, len); + for (int i = len; i < maxLen; i++) + this.data[baseOffset + offset + i] = 0; + } } #endregion } diff --git a/ChanSort.Api/Utils/DvbStringDecoder.cs b/ChanSort.Api/Utils/DvbStringDecoder.cs index 2bfbc96..0153ed1 100644 --- a/ChanSort.Api/Utils/DvbStringDecoder.cs +++ b/ChanSort.Api/Utils/DvbStringDecoder.cs @@ -70,7 +70,8 @@ namespace ChanSort.Api null, "iso-8859-5", "iso-8859-6", "iso-8859-7", "iso-8859-8", "iso-8859-9", "iso-8859-10", "iso-8859-11", null, "iso-8859-13", "iso-8859-14", "iso-8859-15", null, null, null, null, null, // codePages2 prefix - "utf-16", "x-cp20949", "x-cp20936", "utf-16", "utf-8", null, null, null + "utf-16", "x-cp20949", "x-cp20936", "utf-16", "utf-8", null, null, null, + "utf-8", null, null, null, "utf-8" }; static readonly string[] codePages2 = @@ -89,49 +90,73 @@ namespace ChanSort.Api public Encoding DefaultEncoding { get; set; } #region GetChannelNames() - public unsafe void GetChannelNames(byte* name, int len, out string longName, out string shortName) + public void GetChannelNames(byte[] name, int off, int len, out string longName, out string shortName) { - StringBuilder sbLong = new StringBuilder(); - StringBuilder sbShort = new StringBuilder(); + longName = ""; + shortName = ""; + if (len == 0) + return; + byte b = name[off]; + if (b == 0) + return; + Decoder decoder = this.DefaultEncoding.GetDecoder(); - bool inShortMode = false; - for (int i = 0; i < len; i++) + bool singleByteChar = true; + if (b < 0x20) { - byte b = name[i]; - if (b == 0x00) - break; - if (b == 0x10) // prefix for 3-byte code page + if (b == 0x10) // prefix for 2-byte code page { - int cpIndex = name[i + 1] * 256 + name[i + 2]; - i += 2; + int cpIndex = name[off + 1] * 256 + name[off + 2]; + off += 2; + len -= 2; SetDecoder(codePages2, cpIndex, ref decoder); - continue; } if (b <= 0x1F) - { SetDecoder(codePages1, b, ref decoder); - continue; - } + singleByteChar = b < 0x10; + ++off; + --len; + } + if (!singleByteChar) + { + char[] buffer = new char[100]; + int l= decoder.GetChars(name, off, len, buffer, 0, false); + longName = new string(buffer, 0, l); + return; + } + + StringBuilder sbLong = new StringBuilder(); + StringBuilder sbShort = new StringBuilder(); + bool inShortMode = false; + for (int c = 0; c < len; c++) + { + int i = off + c; + b = name[i]; + if (b == 0x00) + break; char ch = '\0'; - switch (b) + if (singleByteChar) { - case 0x86: inShortMode = true; break; - case 0x87: inShortMode = false; break; - case 0x8a: ch = '\n'; break; - default: - // read as many bytes as necessary to get a character - char[] charArray = new char[1]; - fixed (char* pCh = charArray) - { - byte* start = name + i; - for (int j = 1; i < len && decoder.GetChars(start, j, pCh, 1, true) == 0; ++j) - ++i; - } - ch = charArray[0]; - break; + switch (b) + { + case 0x86: inShortMode = true; continue; + case 0x87: inShortMode = false; continue; + case 0x8a: ch = '\n'; break; + default: + if (b >= 0x80 && b <= 0x9f) // DVB-S control characters + continue; + break; + } + } + if (ch == '\0') + { + // read as many bytes as necessary to get a character + char[] charArray = new char[1]; + for (int byteCnt = 1; decoder.GetChars(name, i, byteCnt, charArray, 0) == 0; byteCnt++) + ++i; + ch = charArray[0]; } - if (ch == '\0') continue; diff --git a/ChanSort.Api/Utils/MappingPool.cs b/ChanSort.Api/Utils/MappingPool.cs index 9329efa..1f0fff0 100644 --- a/ChanSort.Api/Utils/MappingPool.cs +++ b/ChanSort.Api/Utils/MappingPool.cs @@ -14,9 +14,9 @@ namespace ChanSort.Api this.caption = caption; } - public void AddMapping(T mapping) + public void AddMapping(int dataLength, T mapping) { - mappings[mapping.DataLength] = mapping; + mappings[dataLength] = mapping; } public T GetMapping(int dataLength, bool throwException = true) diff --git a/ChanSort.Api/Utils/Tools.cs b/ChanSort.Api/Utils/Tools.cs index 75c4809..43a9918 100644 --- a/ChanSort.Api/Utils/Tools.cs +++ b/ChanSort.Api/Utils/Tools.cs @@ -23,5 +23,18 @@ namespace ChanSort.Api name = name.Substring(0, idx); return name; } + + public static string GetAnalogChannelNumber(int freq) + { + if (freq < 41) return ""; + if (freq <= 68) return ((freq - 41)/7 + 1).ToString("d2"); // Band I (01-04) + if (freq < 105) return ""; + if (freq <= 174) return "S" + ((freq - 105)/7 + 1).ToString("d2"); // Midband (S01-S10) + if (freq <= 230) return ((freq - 175)/7 + 5).ToString("d2"); // Band III (05-12) + if (freq <= 300) return "S" + ((freq - 231)/7 + 11); // Superband (S11-S20) + if (freq <= 469) return "S" + ((freq - 303)/8 + 21); // Hyperband (S21-S41) + if (freq <= 1000) return ((freq - 471)/8 + 21).ToString("d2"); // Band IV, V + return ""; + } } } diff --git a/ChanSort.Plugin.ScmFile/AnalogChannel.cs b/ChanSort.Plugin.ScmFile/AnalogChannel.cs new file mode 100644 index 0000000..b3ad71e --- /dev/null +++ b/ChanSort.Plugin.ScmFile/AnalogChannel.cs @@ -0,0 +1,29 @@ +using ChanSort.Api; + +namespace ChanSort.Loader.ScmFile +{ + internal class AnalogChannel : ScmChannelBase + { + private const string _Skip = "Skip"; + private const string _Frequency = "offFrequency"; + + #region ctor() + + public AnalogChannel(int slot, SignalSource signalSource, DataMapping mapping, decimal freq) : base(mapping) + { + this.InitCommonData(slot, signalSource, mapping); + + this.FreqInMhz = (decimal)mapping.GetFloat(_Frequency); // C,D,E series have the value in the data record + if (this.FreqInMhz == 0) // for B series take it from the Tuning table + this.FreqInMhz = freq; + if (this.FreqInMhz == 0) // fallback since Freq is part of the UID and requires a unique value + this.FreqInMhz = slot; + this.Skip = mapping.GetFlag(_Skip); + this.ChannelOrTransponder = ""; + } + + #endregion + + } + +} diff --git a/ChanSort.Plugin.ScmFile/AnalogChannelDataMapping.cs b/ChanSort.Plugin.ScmFile/AnalogChannelDataMapping.cs deleted file mode 100644 index 7d0f971..0000000 --- a/ChanSort.Plugin.ScmFile/AnalogChannelDataMapping.cs +++ /dev/null @@ -1,72 +0,0 @@ -using System.Text; -using ChanSort.Api; - -namespace ChanSort.Plugin.ScmFile -{ - internal class AnalogChannelDataMapping : ChannelMappingBase - { - const string offFrequency = "offFrequency"; - const string offChecksum = "offChecksum"; - - #region ctor() - public AnalogChannelDataMapping(IniFile.Section settings, int length) : - base(settings, length, new UnicodeEncoding(true, false)) - { - } - #endregion - - #region Favorites - public override Favorites Favorites - { - get - { - if (this.DataLength < 64) - return base.Favorites; - - byte fav = 0; - byte mask = 0x01; - foreach (int off in this.GetOffsets(offFavorites)) - { - if (this.GetByte(off) == 1) - fav |= mask; - mask <<= 1; - } - return (Favorites)fav; - } - set - { - if (this.DataLength < 64) - { - base.Favorites = value; - return; - } - - int intValue = (int)value; - foreach (int off in this.GetOffsets(offFavorites)) - { - if ((intValue & 1) != 0) - this.SetByte(off, 1); - intValue >>= 1; - } - } - } - #endregion - - #region Frequency - public float Frequency - { - get { return this.GetFloat(offFrequency); } - set { this.SetFloat(offFrequency, value); } - } - #endregion - - #region Checksum - public byte Checksum - { - get { return this.GetByte(offChecksum); } - set { this.SetByte(offChecksum, value); } - } - #endregion - } - -} diff --git a/ChanSort.Plugin.ScmFile/ChanSort.Plugin.ScmFile.csproj b/ChanSort.Plugin.ScmFile/ChanSort.Loader.ScmFile.csproj similarity index 88% rename from ChanSort.Plugin.ScmFile/ChanSort.Plugin.ScmFile.csproj rename to ChanSort.Plugin.ScmFile/ChanSort.Loader.ScmFile.csproj index 1bec959..590b710 100644 --- a/ChanSort.Plugin.ScmFile/ChanSort.Plugin.ScmFile.csproj +++ b/ChanSort.Plugin.ScmFile/ChanSort.Loader.ScmFile.csproj @@ -8,8 +8,8 @@ {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5} Library Properties - ChanSort.Plugin.ScmFile - ChanSort.Plugin.ScmFile + ChanSort.Loader.ScmFile + ChanSort.Loader.ScmFile v3.5 512 Client @@ -37,7 +37,7 @@ true ..\Debug\ DEBUG;TRACE - true + false full x86 prompt @@ -67,14 +67,15 @@ - - - + + + + + + - - @@ -82,11 +83,6 @@ ChanSort.Api - - - Always - - + \ No newline at end of file diff --git a/ChanSort.Plugin.TllFile2/ChanSort.Plugin.TllFile2.ini b/ChanSort.Plugin.TllFile2/ChanSort.Plugin.TllFile2.ini new file mode 100644 index 0000000..d018b0a --- /dev/null +++ b/ChanSort.Plugin.TllFile2/ChanSort.Plugin.TllFile2.ini @@ -0,0 +1,334 @@ +; FileConfigurationX: overall file and DVB-S data layout +; ACTChannelDataMappingX: analog, DVB-C and DVB-T channel data mapping for data length X + + +[ACTChannelDataMapping:192] + ; LM series with Firmware 4.x (all except LM611S and LM340S) + reorderChannelData = 0 + lenName = 40 + offChannelTransponder = 10, 94, 126, 132 + offProgramNr = 12, 128 + offFavorites = 20 + offPcrPid = 22, 180 + offAudioPid = 24 + offVideoPid = 26 + offName = 30, 140 + offNameLength = 70, 139 + offServiceId = 72, 136 + offFrequencyLong = 96 + offOriginalNetworkId = 102 + offTransportStreamId = 104 + offFavorites2 = 134 + offDeleted = 134 + maskDeleted = 0x42 + offLock = 135 + maskLock = 0x01 + offSkip = 135 + maskSkip = 0x02 + offHide = 135 + maskHide = 0x04 + offServiceType = 138 + offAudioPid2 = 182 + +[ACTChannelDataMapping:188] + ; LM series with Firmware 3.x (LM611S with exceptions, LM340S) + reorderChannelData = 0 + lenName = 40 + offChannelTransponder = 10, 94, 125, 132 + offProgramNr = 12, 128 + offFavorites = 20 + offPcrPid = 22, 180 + offAudioPid = 24 + offVideoPid = 26 + offName = 30, 140 + offNameLength = 70, 139 + offServiceId = 72, 136 + offFrequencyLong = 96 + offOriginalNetworkId = 102 + offTransportStreamId = 104 + offFavorites2 = 134 + offDeleted = 134 + maskDeleted = 0x42 + offLock = 135 + maskLock = 0x01 + offSkip = 135 + maskSkip = 0x02 + offHide = 135 + maskHide = 0x04 + offServiceType = 138 + offAudioPid2 = 182 + +[ACTChannelDataMapping:184] + ; LV470S,LV570S,LV579S(with exceptions), LW5500,LW5590,LW570S,LW579S,LW650S,LW659S(with exceptions) + ; LK950S, CS460S, PM670S, LM611S(with exceptions) + reorderChannelData = 0 + lenName = 40 + offChannelTransponder = 10, 90, 121, 128 + offProgramNr = 12, 124 + offFavorites = 20 + offPcrPid = 22, 176 + offAudioPid = 24 + offVideoPid = 26 + offName = 30, 136 + offNameLength = 70, 135 + offServiceId = 72, 132 + offFrequencyLong = 92 + offOriginalNetworkId = 98 + offTransportStreamId = 100 + offFavorites2 = 130 + offDeleted = 130 + maskDeleted = 0x42 + offLock = 131 + maskLock = 0x01 + offSkip = 131 + maskSkip = 0x02 + offHide = 131 + maskHide = 0x04 + offServiceType = 134 + offAudioPid2 = 178 + +[ACTChannelDataMapping:180] + ; PT + reorderChannelData = 0 + lenName = 40 + offChannelTransponder = 10, 90, 124 + offProgramNr = 12 + offFavorites = 20 + offPcrPid = 22, 172 + offAudioPid = 24 + offVideoPid = 26 + offName = 30, 132 + offNameLength = 70, 131 + offServiceId = 72, 128 + offFrequencyLong = 92 + offOriginalNetworkId = 98 + offTransportStreamId = 100 + offProgramNr2 = 120 + offFavorites2 = 126 + offDeleted = 126 + maskDeleted = 0x42 + offLock = 127 + maskLock = 0x01 + offSkip = 127 + maskSkip = 0x02 + offHide = 127 + maskHide = 0x04 + offServiceType = 130 + offAudioPid2 = 172 + +[ACTChannelDataMapping:176] + ; LD, LE series, LK450, LW4500, LW5400 + reorderChannelData = 0 + lenName = 40 + offChannelTransponder = 10, 86, 120 + offProgramNr = 12 + offFavorites = 20 + offPcrPid = 22, 168 + offAudioPid = 24 + offVideoPid = 26 + offName = 30, 128 + offNameLength = 70, 127 + offServiceId = 72, 124 + offFrequencyLong = 88 + offOriginalNetworkId = 94 + offTransportStreamId = 96 + offProgramNr2 = 116 + offFavorites2 = 122 + offDeleted = 122 + maskDeleted = 0x42 + offLock = 123 + maskLock = 0x01 + offSkip = 123 + maskSkip = 0x02 + offHide = 123 + maskHide = 0x04 + offServiceType = 126 + offAudioPid2 = 170 + +[ACTChannelDataMapping:164] + ; DM and LH series + reorderChannelData = 1 + lenName = 40 + offChannelTransponder = 9, 112 + offProgramNr = 10 + offFavorites = 18 + offPcrPid = 20, 156 + offAudioPid = 22 + offVideoPid = 24 + offName = 28, 116 + offNameLength = 68 + offServiceId = 70 + offOriginalNetworkId = 86 + offTransportStreamId = 88 + offFrequencyLong = 96 + offProgramNr2 = 108 + offFavorites2 = 113 + offDeleted = 113 + maskDeleted = 0x42 + offLock = 113 + maskLock = + offSkip = 113 + maskSkip = 0x20 + offHide = 113 + maskHide = + offServiceType = 115 + offAudioPid2 = 158 + +[DvbsBlock:687880] + ; everything before LM series (but including LM611S and LM340S) + satCount = 64 + satLength = 44 + transponderCount = 2400 + transponderLength = 40 + dvbsChannelCount = 7520 + dvbsChannelLength = 68 + lnbCount = 40 + lnbLength = 44 + +[DvbsBlock:717960] + ; LM and PM series except LM611S and LM340S + satCount = 64 + satLength = 44 + transponderCount = 2400 + transponderLength = 40 + dvbsChannelCount = 7520 + dvbsChannelLength = 72 + lnbCount = 40 + lnbLength = 44 + +[SatChannelDataMapping:68] + lenName = 40 + offSatelliteNr = 0 + offSourceType = 4 + offTransponderIndex = 5, 12 + offProgramNr = 8 + offProgramNrPreset = 10 + offFavorites2 = 14 + offDeleted = 14 + maskDeleted = 0x42 + offEncrypted = 14 + maskEncrypted = 0x80 + offLock = 15 + maskLock = 0x01 + offSkip = 15 + maskSkip = 0x02 + offHide = 15 + maskHide = 0x04 + offProgNrCustomized = 15 + maskProgNrCustomized = 0x40 + offServiceId = 16 + offServiceType = 18 + offNameLength = 19 + offName = 20 + offVideoPid = 60 + offAudioPid = 62 + +[SatChannelDataMapping:72] + lenName = 40 + offSatelliteNr = 0 + offSourceType = 4 + offTransponderIndex = 6, 12 + offProgramNr = 8 + offProgramNrPreset = 10 + offFavorites2 = 14 + offDeleted = 14 + maskDeleted = 0x42 + offEncrypted = 14 + maskEncrypted = 0x80 + offLock = 15 + maskLock = 0x01 + offSkip = 15 + maskSkip = 0x02 + offHide = 15 + maskHide = 0x04 + offProgNrCustomized = 15 + maskProgNrCustomized = 0x40 + offServiceId = 16 + offServiceType = 18 + offNameLength = 19 + offName = 20 + offVideoPid = 60 + offAudioPid = 62 + +[FirmwareData:6944] + ; LH series + offSize = 0 + offHotelModeEnabled=6543 + offHotelModeDtvUpdate=6553 + +[FirmwareData:11008] + ; DM (2350D) + offSize = 0 + offHotelModeEnabled=10563 + offHotelModeDtvUpdate=10573 + +[FirmwareData:15936] + ; PT + offSize = 0 + offHotelModeEnabled=12601 + offHotelModeDtvUpdate=12611 + +[FirmwareData:15960] + ; LW4500, LW5400 + offSize = 0 + offHotelModeEnabled=12603 + offHotelModeDtvUpdate=12613 + +[FirmwareData:16024] + ; LM611S, LM340S, CS460S + offSize = 0 + offHotelModeEnabled=12639 + offHotelModeDtvUpdate=12649 + +[FirmwareData:23072] + ; LD420, LD450, LD550 + offSize = 0 + offHotelModeEnabled=19721 + offHotelModeDtvUpdate=19731 + +[FirmwareData:23088] + ; LK450 + offSize = 0 + offHotelModeEnabled=19723 + offHotelModeDtvUpdate=19733 + +[FirmwareData:23096] + ; LE5500, LD750 + offSize = 0 + offHotelModeEnabled=19721 + offHotelModeDtvUpdate=19731 + +[FirmwareData:35504] + ; LV,LW,LK950S + offSize = 0 + offSystemLock = + offTvPassword = + offHbbTvEnabled = + offHotelModeEnabled=34643 + offHotelModeDtvUpdate=34653 + offHotelMenuAccessCode = 34668 + offHotelMenuPin = 34714 + +[FirmwareData:36856] + ; LM860V + offSize = 0 + offSystemLock = 171 + offTvPassword = 173 + offHbbTvEnabled = 35096 + offHotelModeEnabled=35635 + offHotelModeDtvUpdate=35645 + offHotelMenuAccessCode = 35660 + offHotelMenuPin = 35706 + offSettingsChannelUpdate=36544 + +[FirmwareData:36864] + ; LM (except LM611S,LM340S and LM860V),PM,LS + offSize = 0 + offSystemLock = 171 + offTvPassword = 173 + offHbbTvEnabled = 35096 + offHotelModeEnabled=35635 + offHotelModeDtvUpdate=35645 + offHotelMenuAccessCode = 35660 + offHotelMenuPin = 35706 + offSettingsChannelUpdate=36544 diff --git a/ChanSort.Plugin.TllFile2/DtvChannel.cs b/ChanSort.Plugin.TllFile2/DtvChannel.cs new file mode 100644 index 0000000..4fd47b8 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/DtvChannel.cs @@ -0,0 +1,24 @@ +using ChanSort.Api; + +namespace ChanSort.Plugin.TllFile +{ + public class DtvChannel : TllChannelBase + { + private const string _ChannelOrTransponder = "offChannelTransponder"; + private const string _FrequencyLong = "offFrequencyLong"; + + /* + offFavorites2 = 134 + offAudioPid2 = 182 + */ + + public DtvChannel(int slot, DataMapping data) : base(data) + { + this.InitCommonData(slot, SignalSource.DvbCT, data); + this.InitDvbData(data); + + this.ChannelOrTransponder = data.GetByte(_ChannelOrTransponder).ToString("d2"); + this.FreqInMhz = (decimal)data.GetDword(_FrequencyLong) / 1000; + } + } +} diff --git a/ChanSort.Plugin.TllFile/ModelConstants.cs b/ChanSort.Plugin.TllFile2/DvbsDataLayout.cs similarity index 64% rename from ChanSort.Plugin.TllFile/ModelConstants.cs rename to ChanSort.Plugin.TllFile2/DvbsDataLayout.cs index c49c9fe..91dbe1b 100644 --- a/ChanSort.Plugin.TllFile/ModelConstants.cs +++ b/ChanSort.Plugin.TllFile2/DvbsDataLayout.cs @@ -1,31 +1,23 @@ namespace ChanSort.Plugin.TllFile { - public class ModelConstants + public class DvbsDataLayout { - public readonly string series; - public readonly byte[] magicBytes; - - public int actChannelLength; // auto-detect - public readonly int satCount; public readonly int satLength; public readonly int sizeOfTransponderBlockHeader; public readonly int transponderCount; public readonly int transponderLength; - public readonly int sizeOfZappingTableEntry = 8; + public readonly int sizeOfChannelIndexTableEntry = 8; public readonly int dvbsMaxChannelCount; public readonly int dvbsChannelLength; public readonly int lnbCount; public readonly int lnbLength; public readonly int[] dvbsSubblockLength; - public bool hasDvbSBlock; - public int firmwareBlockLength; // auto-detect + public int LnbBlockHeaderSize = 12; - public ModelConstants(Api.IniFile.Section iniSection) + public DvbsDataLayout(Api.IniFile.Section iniSection) { - this.series = iniSection.Name; - this.magicBytes = iniSection.GetBytes("magicBytes"); this.satCount = iniSection.GetInt("satCount"); this.satLength = iniSection.GetInt("satLength"); this.transponderCount = iniSection.GetInt("transponderCount"); @@ -38,11 +30,11 @@ this.dvbsSubblockLength = new[] { - 12, - 14 + 2 + this.satCount + this.satCount*this.satLength, // 2896 - sizeOfTransponderBlockHeader - 4 + transponderCount * transponderLength, // 110712 - 12 + dvbsMaxChannelCount/8 + dvbsMaxChannelCount*sizeOfZappingTableEntry + dvbsMaxChannelCount * dvbsChannelLength, // 602552 - 8 + lnbCount * lnbLength // 1768 + 12, // header + 14 + 2 + this.satCount + this.satCount*this.satLength, // satellites + sizeOfTransponderBlockHeader - 4 + transponderCount * transponderLength, // transponder + 12 + dvbsMaxChannelCount/8 + dvbsMaxChannelCount*sizeOfChannelIndexTableEntry + dvbsMaxChannelCount * dvbsChannelLength, // channels + LnbBlockHeaderSize - 4 + lnbCount * lnbLength // sat/LNB-Config }; } } diff --git a/ChanSort.Plugin.TllFile/FirmwareDataMapping.cs b/ChanSort.Plugin.TllFile2/FirmwareData.cs similarity index 69% rename from ChanSort.Plugin.TllFile/FirmwareDataMapping.cs rename to ChanSort.Plugin.TllFile2/FirmwareData.cs index 8ecbac9..a1136d0 100644 --- a/ChanSort.Plugin.TllFile/FirmwareDataMapping.cs +++ b/ChanSort.Plugin.TllFile2/FirmwareData.cs @@ -2,7 +2,7 @@ namespace ChanSort.Plugin.TllFile { - public class FirmwareDataMapping : DataMapping + public class FirmwareData : DataMapping { private const string offSize = "offSize"; private const string offSystemLock = "offSystemLock"; @@ -10,20 +10,16 @@ namespace ChanSort.Plugin.TllFile private const string offHbbTvEnabled = "offHbbTvEnabled"; private const string offHotelModeEnabled = "offHotelModeEnabled"; private const string offHotelModeDtvUpdate = "offHotelModeDtvUpdate"; - private const string offHotelMenuAccessCode = "offHotelMenuAccessCode"; - private const string offHotelMenuPin = "offHotelMenuPin"; private const string offSettingsChannelUpdate = "offSettingsChannelUpdate"; - public FirmwareDataMapping(IniFile.Section settings, int structureLength) : - base(settings, structureLength, null) + public FirmwareData(IniFile.Section settings) : + base(settings) { } - public uint Size { get { return this.GetDword(offSize); } } + public long Size { get { return this.GetDword(offSize); } } public bool SystemLocked { get { return this.GetByte(offSystemLock) != 0; } } - public string TvPassword { get { return CodeToString(this.GetDword(offTvPassword)); } } - public string HotelMenuAccessCode { get { return CodeToString(this.GetDword(offHotelMenuAccessCode)); } } - public string HotelMenuPin { get { return CodeToString(this.GetDword(offHotelMenuPin)); } } + public string TvPassword { get { return CodeToString((uint)this.GetDword(offTvPassword)); } } public bool SettingsAutomaticChannelUpdate diff --git a/ChanSort.Plugin.TllFile2/Properties/AssemblyInfo.cs b/ChanSort.Plugin.TllFile2/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..c034adf --- /dev/null +++ b/ChanSort.Plugin.TllFile2/Properties/AssemblyInfo.cs @@ -0,0 +1,38 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +[assembly: InternalsVisibleTo("Test.Plugin.TllFile")] + +// General Information about an assembly is controlled through the following +// set of attributes. Change these attribute values to modify the information +// associated with an assembly. +[assembly: AssemblyTitle("ChanSort.Plugin.TllFile2")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("ChanSort.Plugin.TllFile2")] +[assembly: AssemblyCopyright("Copyright © 2013")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Setting ComVisible to false makes the types in this assembly not visible +// to COM components. If you need to access a type in this assembly from +// COM, set the ComVisible attribute to true on that type. +[assembly: ComVisible(false)] + +// The following GUID is for the ID of the typelib if this project is exposed to COM +[assembly: Guid("f4702e0e-8277-44c6-b709-4d1c78654837")] + +// Version information for an assembly consists of the following four values: +// +// Major Version +// Minor Version +// Build Number +// Revision +// +// You can specify all the values or you can default the Build and Revision Numbers +// by using the '*' as shown below: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/ChanSort.Plugin.TllFile2/Resource.Designer.cs b/ChanSort.Plugin.TllFile2/Resource.Designer.cs new file mode 100644 index 0000000..3ddf7b2 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/Resource.Designer.cs @@ -0,0 +1,108 @@ +//------------------------------------------------------------------------------ +// +// This code was generated by a tool. +// Runtime Version:4.0.30319.586 +// +// Changes to this file may cause incorrect behavior and will be lost if +// the code is regenerated. +// +//------------------------------------------------------------------------------ + +namespace ChanSort.Plugin.TllFile { + using System; + + + /// + /// A strongly-typed resource class, for looking up localized strings, etc. + /// + // This class was auto-generated by the StronglyTypedResourceBuilder + // class via a tool like ResGen or Visual Studio. + // To add or remove a member, edit your .ResX file then rerun ResGen + // with the /str option, or rebuild your VS project. + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")] + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] + internal class Resource { + + private static global::System.Resources.ResourceManager resourceMan; + + private static global::System.Globalization.CultureInfo resourceCulture; + + [global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")] + internal Resource() { + } + + /// + /// Returns the cached ResourceManager instance used by this class. + /// + [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] + internal static global::System.Resources.ResourceManager ResourceManager { + get { + if (object.ReferenceEquals(resourceMan, null)) { + global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("ChanSort.Plugin.TllFile.Resource", typeof(Resource).Assembly); + resourceMan = temp; + } + return resourceMan; + } + } + + /// + /// Overrides the current thread's CurrentUICulture property for all + /// resource lookups using this strongly typed resource class. + /// + [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] + internal static global::System.Globalization.CultureInfo Culture { + get { + return resourceCulture; + } + set { + resourceCulture = value; + } + } + + /// + /// Looks up a localized string similar to Channel #{0} (Pr# {1}) was erased because it is a duplicate of channel #{2} (Pr# {3}): {4}. + /// + internal static string TllFileSerializer_ERR_dupeChannel { + get { + return ResourceManager.GetString("TllFileSerializer_ERR_dupeChannel", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Wrong checksum: calculated {1:x8} but file has {0:x8}. + /// + internal static string TllFileSerializer_ERR_wrongChecksum { + get { + return ResourceManager.GetString("TllFileSerializer_ERR_wrongChecksum", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to File size {0} is larger than allowed maxiumum of {1}. + /// + internal static string TllFileSerializerPlugin_ERR_fileTooBig { + get { + return ResourceManager.GetString("TllFileSerializerPlugin_ERR_fileTooBig", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to The file content doesn't match any supported model. + /// + internal static string TllFileSerializerPlugin_ERR_modelUnknown { + get { + return ResourceManager.GetString("TllFileSerializerPlugin_ERR_modelUnknown", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to LG-Electronics *.tll Loader. + /// + internal static string TllFileSerializerPlugin_PluginName { + get { + return ResourceManager.GetString("TllFileSerializerPlugin_PluginName", resourceCulture); + } + } + } +} diff --git a/ChanSort.Plugin.TllFile2/Resource.de.Designer.cs b/ChanSort.Plugin.TllFile2/Resource.de.Designer.cs new file mode 100644 index 0000000..e69de29 diff --git a/ChanSort.Plugin.TllFile2/Resource.de.resx b/ChanSort.Plugin.TllFile2/Resource.de.resx new file mode 100644 index 0000000..1cd6f3a --- /dev/null +++ b/ChanSort.Plugin.TllFile2/Resource.de.resx @@ -0,0 +1,135 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + Prüfsummenfehler: berechnet wurde {1:x8} aber Datei enthält {0:x8} + + + Der Dateiinhalt entstpricht keinem bekannten Modell + + + Dateigröße {0} überschreitet das erlaubte Maximum von {1} + + + LG-Electronics *.tll Loader + + + Sender #{0} (Pr# {1}) wurde gelöscht da er ein Duplikat von Sender #{2} (Pr# {3}) ist: {4} + + \ No newline at end of file diff --git a/ChanSort.Plugin.TllFile2/Resource.resx b/ChanSort.Plugin.TllFile2/Resource.resx new file mode 100644 index 0000000..55d3e21 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/Resource.resx @@ -0,0 +1,116 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 1.3 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.3500.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.3500.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + Wrong checksum: calculated {1:x8} but file has {0:x8} + + + The file content doesn't match any supported model + + + File size {0} is larger than allowed maxiumum of {1} + + + LG-Electronics *.tll Loader + + + Channel #{0} (Pr# {1}) was erased because it is a duplicate of channel #{2} (Pr# {3}): {4} + + \ No newline at end of file diff --git a/ChanSort.Plugin.TllFile2/SatChannel.cs b/ChanSort.Plugin.TllFile2/SatChannel.cs new file mode 100644 index 0000000..016c92a --- /dev/null +++ b/ChanSort.Plugin.TllFile2/SatChannel.cs @@ -0,0 +1,44 @@ +using ChanSort.Api; + +namespace ChanSort.Plugin.TllFile +{ + class SatChannel : TllChannelBase + { + private const string _SatConfigIndex = "offSatelliteNr"; + private const string _TransponderIndex = "offTransponderIndex"; + + public bool InUse { get; private set; } + + public SatChannel(int order, int slot, DataMapping data, DataRoot dataRoot) : base(data) + { + this.InUse = data.GetWord(_SatConfigIndex) != 0xFFFF; + if (!InUse) + return; + + this.InitCommonData(slot, SignalSource.DvbS, data); + this.InitDvbData(data); + + int transponderIndex = data.GetWord(_TransponderIndex); + Transponder transponder = dataRoot.Transponder.TryGet(transponderIndex); + Satellite sat = transponder.Satellite; + + this.Satellite = sat.Name; + this.SatPosition = sat.OrbitalPosition; + this.RecordOrder = order; + this.TransportStreamId = transponder.TransportStreamId; + this.OriginalNetworkId = transponder.OriginalNetworkId; + this.SymbolRate = transponder.SymbolRate; + this.Polarity = transponder.Polarity; + this.FreqInMhz = transponder.FrequencyInMhz; + } + + public override void UpdateRawData() + { + base.UpdateRawData(); + +// bool deleted = this.NewProgramNr == 0; +// if (deleted) + // mapping.SetWord(_SatConfigIndex, 0xFFFF); + } + } +} diff --git a/ChanSort.Plugin.TllFile2/SatChannelListHeader.cs b/ChanSort.Plugin.TllFile2/SatChannelListHeader.cs new file mode 100644 index 0000000..8880b32 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/SatChannelListHeader.cs @@ -0,0 +1,19 @@ +using System; + +namespace ChanSort.Plugin.TllFile +{ + internal class SatChannelListHeader + { + private readonly byte[] data; + private readonly int baseOffset; + public SatChannelListHeader(byte[] data, int offset) { this.data = data; this.baseOffset = offset; } + + public uint Checksum { get { return BitConverter.ToUInt32(data, baseOffset + 0); } } + public int LinkedListStartIndex { get { return BitConverter.ToInt16(data, baseOffset + 8); }} + public int LinkedListEndIndex1 { get { return BitConverter.ToInt16(data, baseOffset + 10); } } + public int LinkedListEndIndex2 { get { return BitConverter.ToInt16(data, baseOffset + 12); } } + public int ChannelCount { get { return BitConverter.ToInt16(data, baseOffset + 14); } } + + public int Size { get { return 16; } } + } +} diff --git a/ChanSort.Plugin.TllFile2/SatTransponder.cs b/ChanSort.Plugin.TllFile2/SatTransponder.cs new file mode 100644 index 0000000..655f6ce --- /dev/null +++ b/ChanSort.Plugin.TllFile2/SatTransponder.cs @@ -0,0 +1,31 @@ +using System; + +namespace ChanSort.Plugin.TllFile +{ + internal class SatTransponder + { + private readonly byte[] data; + public int BaseOffset { get; set; } + + public SatTransponder(byte[] data) + { + this.data = data; + } + + public int Frequency { get { return BitConverter.ToInt16(data, BaseOffset + 12); } } + public int OriginalNetworkId { get { return BitConverter.ToInt16(data, BaseOffset + 18); } } + public int TransportStreamId { get { return BitConverter.ToInt16(data, BaseOffset + 20); } } + + public int SymbolRate + { + get { return BitConverter.ToInt16(data, BaseOffset + 25); } + set + { + data[BaseOffset + 25] = (byte)value; + data[BaseOffset + 26] = (byte)(value >> 8); + } + } + + public int SatIndex { get { return data[BaseOffset + 36]; } } + } +} diff --git a/ChanSort.Plugin.TllFile2/TllChannelBase.cs b/ChanSort.Plugin.TllFile2/TllChannelBase.cs new file mode 100644 index 0000000..4307a80 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/TllChannelBase.cs @@ -0,0 +1,134 @@ +using ChanSort.Api; + +namespace ChanSort.Plugin.TllFile +{ + public class TllChannelBase : ChannelInfo + { + // common + private const string _ProgramNr = "offProgramNr"; + private const string _ProgramNr2 = "offProgramNr2"; // not for DVB-S + private const string _Name = "offName"; + private const string _NameLength = "offNameLength"; + private const string _Favorites = "offFavorites"; // not for DVB-S + + private const string _Deleted = "Deleted"; // hack + private const string _Favorites2 = "offFavorites2"; + private const string _Encrypted = "Encrypted"; + + private const string _Lock = "Lock"; + private const string _Skip = "Skip"; + private const string _Hide = "Hide"; + private const string _Moved = "ProgNrCustomized"; + + // DVB + private const string _ServiceId = "offServiceId"; + private const string _VideoPid = "offVideoPid"; + private const string _AudioPid = "offAudioPid"; + private const string _OriginalNetworkId = "offOriginalNetworkId"; + private const string _TransportStreamId = "offTransportStreamId"; + private const string _ServiceType = "offServiceType"; + + protected readonly DataMapping mapping; + protected readonly byte[] rawData; + internal readonly int baseOffset; + + public bool IsDeleted { get; set; } + + protected TllChannelBase(DataMapping data) + { + this.mapping = data; + this.rawData = data.Data; + this.baseOffset = data.BaseOffset; + } + + #region InitCommonData() + protected void InitCommonData(int slot, SignalSource signalSource, DataMapping data) + { + this.RecordIndex = slot; + this.SignalSource = signalSource; + var nr = data.GetWord(_ProgramNr); + this.SignalType = this.GetSignalType(nr); + this.OldProgramNr = (nr & 0x3FFF); + + this.ParseNames(); + + this.Favorites = (Favorites)((data.GetByte(_Favorites2) & 0x3C) >> 2); + this.Lock = data.GetFlag(_Lock); + this.Skip = data.GetFlag(_Skip); + this.Hidden = data.GetFlag(_Hide); + this.Encrypted = data.GetFlag(_Encrypted); + this.IsDeleted = data.GetFlag(_Deleted); + } + #endregion + + #region InitDvbData() + protected void InitDvbData(DataMapping data) + { + this.ServiceId = data.GetWord(_ServiceId); + //this.PcrPid = data.GetWord(_PcrPid); + this.VideoPid = data.GetWord(_VideoPid); + this.AudioPid = data.GetWord(_AudioPid); + this.OriginalNetworkId = data.GetWord(_OriginalNetworkId); + this.TransportStreamId = data.GetWord(_TransportStreamId); + this.ServiceType = data.GetByte(_ServiceType); + } + #endregion + + #region GetSignalType() + protected SignalType GetSignalType(uint programNr) + { + if ((programNr & 0x4000) != 0) + return SignalType.Radio; + return SignalType.Tv; + } + #endregion + + #region ParseNames() + private void ParseNames() + { + mapping.SetDataPtr(this.rawData, this.baseOffset); + DvbStringDecoder dec = new DvbStringDecoder(mapping.DefaultEncoding); + string longName, shortName; + dec.GetChannelNames(this.rawData, this.baseOffset + mapping.GetOffsets(_Name)[0], mapping.GetByte(_NameLength), + out longName, out shortName); + this.Name = longName; + this.ShortName = shortName; + } + #endregion + + #region UpdateRawData() + public override void UpdateRawData() + { + mapping.SetDataPtr(this.rawData, this.baseOffset); + mapping.SetWord(_ProgramNr, this.NewProgramNr + (this.SignalType == SignalType.Radio ? 0x4000 : 0)); + mapping.SetWord(_ProgramNr2, (mapping.GetWord(_ProgramNr2) & 0x0003) | (this.NewProgramNr << 2)); + if (this.IsNameModified) + { + mapping.SetString(_Name, this.Name, 40); + mapping.SetByte(_NameLength, this.Name.Length); + this.IsNameModified = false; + } + mapping.SetByte(_Favorites2, (mapping.GetByte(_Favorites2)) & 0xC3 | ((byte) this.Favorites << 2)); + mapping.SetByte(_Favorites, (mapping.GetByte(_Favorites) & 0xF0) | (byte)this.Favorites); + mapping.SetFlag(_Skip, this.Skip); + mapping.SetFlag(_Lock, this.Lock); + mapping.SetFlag(_Hide, this.Hidden); + if (this.NewProgramNr == 0) + { + mapping.SetFlag(_Deleted, true); + mapping.SetByte("off"+_Moved, 0); //skip,lock,hide,moved + } + else + mapping.SetFlag(_Moved, true); + } + #endregion + + #region ChangeEncoding() + public override void ChangeEncoding(System.Text.Encoding encoding) + { + this.mapping.DefaultEncoding = encoding; + this.ParseNames(); + } + #endregion + } +} diff --git a/ChanSort.Plugin.TllFile2/TllFileSerializer.cs b/ChanSort.Plugin.TllFile2/TllFileSerializer.cs new file mode 100644 index 0000000..42d1869 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/TllFileSerializer.cs @@ -0,0 +1,722 @@ +#define FIX_SYMBOL_RATE + +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Reflection; +using System.Text; +using System.Windows.Forms; +using ChanSort.Api; + +namespace ChanSort.Plugin.TllFile +{ + public class TllFileSerializer : SerializerBase + { + private const long MaxFileSize = 2000000; + private readonly string ERR_fileTooBig = Resource.TllFileSerializerPlugin_ERR_fileTooBig; + private readonly string ERR_modelUnknown = Resource.TllFileSerializerPlugin_ERR_modelUnknown; + private readonly string ERR_wrongChecksum = Resource.TllFileSerializer_ERR_wrongChecksum; + private readonly string ERR_dupeChannel = Resource.TllFileSerializer_ERR_dupeChannel; + + private readonly MappingPool actMappings = new MappingPool("Analog and DVB-C/T"); + private readonly MappingPool dvbsMappings = new MappingPool("DVB-S"); + private readonly MappingPool firmwareMappings = new MappingPool("Firmware"); + private readonly Dictionary satConfigs = new Dictionary(); + + private byte[] fileContent; + + private int analogBlockOffset; + private int firmwareBlockOffset; + private int dvbctBlockOffset; + private int dvbsBlockOffset; + private int[] dvbsSubblockCrcOffset; + private int settingsBlockOffset; + + private int actChannelSize; + private bool reorderPhysically; + + private int analogChannelCount; + private int dvbctChannelCount; + private int dvbsChannelCount; + + private DvbsDataLayout satConfig; + private bool isDvbsSymbolRateDiv2; + + private Dictionary nextChannelIndex; + private int firmwareBlockSize; + private int dvbsBlockSize; + private int settingsBlockSize; + private string countryCode; + + private int duplicateChannels; + private int deletedChannelsHard; + private int deletedChannelsSoft; + private int dvbsChannelsAtPr0; + + private bool removeDeletedActChannels; + + #region ctor() + public TllFileSerializer(string inputFile) : base(inputFile) + { + + this.Features.ChannelNameEdit = true; + this.Features.EraseChannelData = true; + this.Features.FileInformation = true; + this.Features.DeviceSettings = true; + this.SupportedTvCountryCodes = new List + { + "___ (None)", "AUT (Austria)", "BEL (Belgium)", "CHE (Switzerland)", + "DEU (Germany)", "ESP (Spain)", "FRA (France)", "GBR (Great Britain)", + "GRC (Greece)", "IRL (Ireland)", "ITA (Italy)", "LUX (Luxembourg)", + "NLD (Netherlands)", "PRT (Portugal)", "SVN (Slovenia)" + }; + + this.ReadConfigurationFromIniFile(); + } + #endregion + + public IList SupportedTvCountryCodes { get; private set; } + + #region ReadConfigurationFromIniFile() + + private void ReadConfigurationFromIniFile() + { + string iniFile = Assembly.GetExecutingAssembly().Location.Replace(".dll", ".ini"); + IniFile ini = new IniFile(iniFile); + foreach (var section in ini.Sections) + { + int idx = section.Name.IndexOf(":"); + int recordLength = idx < 0 ? 0 : int.Parse(section.Name.Substring(idx + 1)); + if (section.Name.StartsWith("DvbsBlock")) + this.satConfigs.Add(recordLength, new DvbsDataLayout(section)); + else if (section.Name.StartsWith("ACTChannelDataMapping")) + actMappings.AddMapping(recordLength, new DataMapping(section)); + else if (section.Name.StartsWith("SatChannelDataMapping")) + dvbsMappings.AddMapping(recordLength, new DataMapping(section)); + else if (section.Name.StartsWith("FirmwareData")) + firmwareMappings.AddMapping(recordLength, new FirmwareData(section)); + } + } + #endregion + + + #region DisplayName + public override string DisplayName { get { return "TLL loader"; } } + #endregion + + #region Load() + + public override void Load() + { + long fileSize = new FileInfo(this.FileName).Length; + if (fileSize > MaxFileSize) + throw new InvalidOperationException(string.Format(ERR_fileTooBig, fileSize, MaxFileSize)); + + this.fileContent = File.ReadAllBytes(this.FileName); + int off = 0; + + this.ReadFileHeader(ref off); + this.ReadAnalogChannelBlock(ref off); + this.ReadFirmwareDataBlock(ref off); + this.ReadDvbCtChannels(ref off); + this.ReadDvbSBlock(ref off); + this.ReadSettingsBlock(ref off); + } + + #endregion + + #region ReadFileHeader() + private void ReadFileHeader(ref int off) + { + if (fileContent.Length < 4) + throw new InvalidOperationException(ERR_modelUnknown); + if (BitConverter.ToUInt32(fileContent, off) == 0x5A5A5A5A) + off += 4; + } + #endregion + + #region ReadAnalogChannelBlock() + + private void ReadAnalogChannelBlock(ref int off) + { + this.analogBlockOffset = off; + this.ReadActChannelBlock(ref off, out analogChannelCount, out actChannelSize, + (slot, data) => new AnalogChannel(slot, data)); + } + #endregion + + #region ReadFirmwareDataBlock() + private void ReadFirmwareDataBlock(ref int off) + { + this.firmwareBlockOffset = off; + this.firmwareBlockSize = this.GetBlockSize(off); + off += 4 + this.firmwareBlockSize; + } + #endregion + + #region ReadDvbCtChannels() + private void ReadDvbCtChannels(ref int off) + { + this.dvbctBlockOffset = off; + this.ReadActChannelBlock(ref off, out dvbctChannelCount, out actChannelSize, + (slot, data) => new DtvChannel(slot, data)); + } + #endregion + + #region ReadDvbSBlock() + private void ReadDvbSBlock(ref int off) + { + int blockSize; + if (!IsDvbsBlock(off, out blockSize)) + return; + + this.dvbsBlockSize = blockSize; + this.dvbsBlockOffset = off; + off += 4; + + this.satConfig = this.satConfigs.TryGet(blockSize); + if (satConfig != null) + this.ReadDvbsSubblocks(ref off); + else + { + this.DataRoot.Warnings.AppendFormat("DVB-S data format is not supported (size={0})\n", blockSize); + off += blockSize; + } + } + #endregion + + #region ReadSettingsBlock() + private void ReadSettingsBlock(ref int off) + { + this.settingsBlockOffset = off; + if (this.settingsBlockOffset >= fileContent.Length) + { + this.settingsBlockOffset = 0; + return; + } + + this.settingsBlockSize = this.GetBlockSize(off); + off += 4; + if (settingsBlockSize >= 8) + { + StringBuilder code = new StringBuilder(); + for (int i = 6; i >= 4; i--) + code.Append((char)fileContent[off + i]); + this.countryCode = code.ToString(); + } + off += settingsBlockSize; + } + #endregion + + + #region ReadActChannelBlock() + private void ReadActChannelBlock(ref int off, out int channelCount, out int recordSize, + Func channelFactory) + { + recordSize = 0; + int blockSize = this.GetBlockSize(off, minSize: 2); + off += 4; + channelCount = BitConverter.ToInt32(fileContent, off); + off += 4; + if (channelCount == 0) return; + + recordSize = GetActChannelRecordSize(off, blockSize, channelCount); + var actMapping = this.actMappings.GetMapping(recordSize); + this.reorderPhysically = actMapping.Settings.GetInt("reorderChannelData") != 0; + + for (int i = 0; i < channelCount; i++) + { + actMapping.SetDataPtr(fileContent, off); + ChannelInfo ci = channelFactory(i, actMapping); + + var list = this.DataRoot.GetChannelList(ci.SignalSource, ci.SignalType, true); + this.DataRoot.AddChannel(list, ci); + + off += recordSize; + } + } + #endregion + + #region GetBlockSize() + private int GetBlockSize(int off, int minSize = 0) + { + long len = BitConverter.ToUInt32(fileContent, off); + if (len < minSize || off + 4 + len > fileContent.Length) + throw new InvalidOperationException(ERR_modelUnknown); + return (int)len; + } + #endregion + + #region GetActChannelRecordSize() + private int GetActChannelRecordSize(int off, int blockSize, int channelCount) + { + if ((blockSize - 4) % channelCount != 0) + throw new InvalidOperationException(ERR_modelUnknown); + int recordSize = (blockSize - 4) / channelCount; + if (off + channelCount * recordSize > fileContent.Length) + throw new InvalidOperationException(ERR_modelUnknown); + return recordSize; + } + #endregion + + + #region IsDvbsBlock() + private bool IsDvbsBlock(int off, out int blockSize) + { + blockSize = 0; + if (off >= fileContent.Length) + return false; + blockSize = this.GetBlockSize(off); + if (blockSize < 12) + return false; + ulong blockId = BitConverter.ToUInt64(fileContent, off + 8); + if (blockId != 0x0032532D53425644) // reverse "DVBS-S2\0" + return false; + return true; + } + #endregion + + #region ReadDvbsSubblocks() + private void ReadDvbsSubblocks(ref int off) + { + this.ScanDvbSSubBlockChecksums(off); + + // subblock 1 (DVBS header) + off += 16; + + // subblock 2 (satellites) + off += 84; // irrelevant data + this.ReadSatellites(ref off); + + // subblock 3 (transponder) + off += satConfig.sizeOfTransponderBlockHeader; + this.ReadTransponderData(ref off); + + // subblock 4 (channels) + SatChannelListHeader header = new SatChannelListHeader(fileContent, off); + this.dvbsChannelCount = header.ChannelCount; + off += header.Size; + off += satConfig.dvbsMaxChannelCount/8; // skip allocation bitmap + this.ReadDvbsChannelLinkedList(ref off); + + this.ReadDvbSChannels(ref off, header.LinkedListStartIndex); + + // subblock 5 (satellite/LNB config) + off += satConfig.LnbBlockHeaderSize + satConfig.lnbCount*satConfig.lnbLength; + } + #endregion + + #region ScanDvbSSubBlockChecksums() + private void ScanDvbSSubBlockChecksums(int off) + { + this.dvbsSubblockCrcOffset = new int[satConfig.dvbsSubblockLength.Length]; + for (int i = 0; i < dvbsSubblockCrcOffset.Length; i++) + { + this.dvbsSubblockCrcOffset[i] = off; + int subblockLength = satConfig.dvbsSubblockLength[i]; + uint fileCrc = BitConverter.ToUInt32(fileContent, off); + uint calcCrc = Crc32.CalcCrc32(fileContent, off + 4, subblockLength); + if (fileCrc != calcCrc) + throw new IOException(string.Format(ERR_wrongChecksum, calcCrc, fileCrc)); + off += 4 + subblockLength; + } + } + #endregion + + #region ReadSatellites() + private void ReadSatellites(ref int off) + { + for (int i = 0; i < satConfig.satCount; i++) + { + Satellite sat = new Satellite(i); + string satName = Encoding.ASCII.GetString(fileContent, off + 0, 32).TrimEnd('\0'); + sat.Name = satName; + sat.OrbitalPosition = GetSatLocation(fileContent[off + 32], fileContent[off + 33]); + this.DataRoot.AddSatellite(sat); + off += satConfig.satLength; + } + } + #endregion + + #region ReadTransponderData() + private void ReadTransponderData(ref int off) + { + var data = new SatTransponder(fileContent); + data.BaseOffset = off; + for (int i=0; i= 95) + data.SymbolRate = (ushort)((data.SymbolRate & 0x8000) | ((sr / 100 + 1) * 100)); +#endif + + Transponder transponder = new Transponder(i); + transponder.FrequencyInMhz = data.Frequency; + transponder.OriginalNetworkId = data.OriginalNetworkId; + transponder.TransportStreamId = data.TransportStreamId; + transponder.SymbolRate = data.SymbolRate & 0x7FFF; + if (data.SymbolRate == 11000) + this.isDvbsSymbolRateDiv2 = true; + + var sat = this.DataRoot.Satellites.TryGet(data.SatIndex/2); + this.DataRoot.AddTransponder(sat, transponder); + + data.BaseOffset += satConfig.transponderLength; + } + + if (this.isDvbsSymbolRateDiv2) + { + foreach (var transponder in this.DataRoot.Transponder.Values) + transponder.SymbolRate *= 2; + } + + off += this.satConfig.transponderCount * this.satConfig.transponderLength; + } + #endregion + + #region ReadDvbsChannelLinkedList() + private void ReadDvbsChannelLinkedList(ref int off) + { + this.nextChannelIndex = new Dictionary(); + for (int i = 0; i < satConfig.dvbsMaxChannelCount; i++) + { + int offEntry = off + i*satConfig.sizeOfChannelIndexTableEntry; + int cur = BitConverter.ToUInt16(fileContent, offEntry + 4); + if (cur != i) + break; + this.nextChannelIndex.Add(cur, BitConverter.ToUInt16(fileContent, offEntry + 2)); + } + off += satConfig.dvbsMaxChannelCount*satConfig.sizeOfChannelIndexTableEntry; + } + #endregion + + #region ReadDvbSChannels() + private void ReadDvbSChannels(ref int off, int startIndex) + { + var mapping = this.dvbsMappings.GetMapping(satConfig.dvbsChannelLength); + int index = startIndex; + for (int i = 0; i < this.dvbsChannelCount; i++) + { + int recordOffset = off + index*satConfig.dvbsChannelLength; + mapping.SetDataPtr(fileContent, recordOffset); + SatChannel ci = new SatChannel(i, index, mapping, this.DataRoot); + if (!ci.InUse) + ++this.deletedChannelsHard; + else if (ci.IsDeleted) + ++this.deletedChannelsSoft; + else + { + var list = this.DataRoot.GetChannelList(ci.SignalSource, ci.SignalType, true); + var dupes = list.GetChannelByUid(ci.Uid); + if (dupes.Count == 0) + { + if (ci.OldProgramNr == 0) + ++this.dvbsChannelsAtPr0; + this.DataRoot.AddChannel(list, ci); + } + else + { + // duplicate channels (ONID,TSID,SSID) cause the TV to randomly reorder channels and show wrong ones in the + // program list, so we erase all dupes here + this.DataRoot.Warnings.AppendFormat(ERR_dupeChannel, ci.RecordIndex, ci.OldProgramNr, dupes[0].RecordIndex, + dupes[0].OldProgramNr, dupes[0].Name).AppendLine(); + this.EraseDuplicateDvbsChannel(recordOffset, satConfig); + ++this.duplicateChannels; + } + } + + if (!this.nextChannelIndex.TryGetValue(index, out index) || index == -1) + break; + } + off += satConfig.dvbsMaxChannelCount * satConfig.dvbsChannelLength; + } + #endregion + + #region EraseDuplicateDvbsChannel() + private void EraseDuplicateDvbsChannel(int off, DvbsDataLayout c) + { + for (int i = 0; i < c.dvbsChannelLength; i++) + fileContent[off++] = 0xFF; + } + #endregion + + #region GetSatLocation() + private string GetSatLocation(byte degree, byte fractionAndOrientation) + { + return string.Format("{0}.{1}{2}", degree, fractionAndOrientation & 0x0f, fractionAndOrientation < 16 ? "W" : "E"); + } + #endregion + + + + #region Save() + public override void Save(string tvOutputFile, string csvOutputFile) + { + int newAnalogChannelCount; + int newDvbctChannelCount; + this.UpdateRawChannelData(out newAnalogChannelCount, out newDvbctChannelCount); + + if (!removeDeletedActChannels) + { + newAnalogChannelCount = this.analogChannelCount; + newDvbctChannelCount = this.dvbctChannelCount; + } + + if (this.reorderPhysically || this.removeDeletedActChannels) + this.ReorderActChannelsPhysically(); + + if (satConfig != null) + this.UpdateDvbsChecksums(); + + using (var file = new BinaryWriter(new FileStream(tvOutputFile, FileMode.Create, FileAccess.Write))) + { + // header + file.Write(this.fileContent, 0, this.analogBlockOffset); + + // analog + file.Write(newAnalogChannelCount*this.actChannelSize + 4); + file.Write(newAnalogChannelCount); + file.Write(fileContent, this.analogBlockOffset + 8, newAnalogChannelCount*this.actChannelSize); + + // firmware + file.Write(fileContent, this.firmwareBlockOffset, this.firmwareBlockSize + 4); + + // DVB-CT + file.Write(newDvbctChannelCount*this.actChannelSize + 4); + file.Write(newDvbctChannelCount); + file.Write(fileContent, this.dvbctBlockOffset + 8, newDvbctChannelCount * this.actChannelSize); + + // DVB-S + if (this.dvbsBlockOffset != 0) + file.Write(fileContent, this.dvbsBlockOffset, this.dvbsBlockSize + 4); + + // rest (including settings) + file.Write(fileContent, this.settingsBlockOffset, fileContent.Length - this.settingsBlockOffset); + } + } + #endregion + + #region UpdateRawChannelData() + private void UpdateRawChannelData(out int newAnalogChannelCount, out int newDvbctChannelCount) + { + newAnalogChannelCount = 0; + newDvbctChannelCount = 0; + foreach (var list in this.DataRoot.ChannelLists) + { + foreach (TllChannelBase channel in list.Channels) + { + if (channel.NewProgramNr != 0) + { + if ((channel.SignalSource & SignalSource.Digital) == 0) + ++newAnalogChannelCount; + else if (channel.SignalSource != SignalSource.DvbS) + ++newDvbctChannelCount; + } + channel.OldProgramNr = channel.NewProgramNr; + channel.UpdateRawData(); + } + } + } + #endregion + + #region ReorderActChannelsPhysically() + private void ReorderActChannelsPhysically() + { + var analogTv = this.DataRoot.GetChannelList(SignalSource.AnalogCT, SignalType.Tv, false); + var analogRadio = this.DataRoot.GetChannelList(SignalSource.AnalogCT, SignalType.Radio, false); + var analog = analogTv.Channels.Union(analogRadio.Channels).ToList(); + this.ReorderChannelData(this.analogBlockOffset + 8, this.actChannelSize, this.analogChannelCount, analog); + + var dvbCtTv = this.DataRoot.GetChannelList(SignalSource.DvbCT, SignalType.Tv, false); + var dvbCtRadio = this.DataRoot.GetChannelList(SignalSource.DvbCT, SignalType.Radio, false); + var dvbCt = dvbCtTv.Channels.Union(dvbCtRadio.Channels).ToList(); + this.ReorderChannelData(this.dvbctBlockOffset + 8, this.actChannelSize, this.dvbctChannelCount, dvbCt); + } + #endregion + + + #region ReorderChannelData() + private void ReorderChannelData(int channelDataOffset, int channelDataLength, int recordCount, IList sortedList) + { + if (sortedList.Count == 0) return; + byte[] copy = new byte[recordCount * channelDataLength]; + Array.Copy(fileContent, channelDataOffset, copy, 0, copy.Length); + + int pTarget = channelDataOffset; + int slot = 0; + foreach (ChannelInfo appChannel in sortedList) + { + if (appChannel.NewProgramNr <= 0 && this.removeDeletedActChannels) + continue; + if (appChannel.RecordIndex != slot) + { + Array.Copy(copy, appChannel.RecordIndex*channelDataLength, fileContent, pTarget, channelDataLength); + appChannel.RecordIndex = slot; + } + ++slot; + pTarget += channelDataLength; + } + } + #endregion + + #region UpdateDvbsChecksums() + private void UpdateDvbsChecksums() + { + for (int i = 0; i < this.dvbsSubblockCrcOffset.Length; i++) + { + uint crc32 = Crc32.CalcCrc32(fileContent, this.dvbsSubblockCrcOffset[i] + 4, satConfig.dvbsSubblockLength[i]); + var bytes = BitConverter.GetBytes(crc32); + for (int j = 0; j < bytes.Length; j++) + fileContent[this.dvbsSubblockCrcOffset[i] + j] = bytes[j]; + } + } + #endregion + + + #region DefaultEncoding + public override Encoding DefaultEncoding + { + get { return base.DefaultEncoding; } + set + { + if (Equals(value, this.DefaultEncoding)) + return; + base.DefaultEncoding = value; + if (this.DataRoot.IsEmpty) + return; + ChangeEncoding(); + } + } + #endregion + + #region ChangeEncoding() + + private void ChangeEncoding() + { + foreach (var list in DataRoot.ChannelLists) + { + foreach (var channel in list.Channels) + channel.ChangeEncoding(this.DefaultEncoding); + } + } + #endregion + + // TvSettingsForm + + #region GetFileInformation() + public override string GetFileInformation() + { + StringBuilder sb = new StringBuilder(); + sb.AppendLine("ANALOG"); + sb.Append("Number of data records: ").Append(this.analogChannelCount).AppendLine(); + sb.Append("Length of data record: ").Append(this.actChannelSize).AppendLine(); + sb.AppendLine(); + + sb.AppendLine(); + sb.AppendLine("DVB-C/T"); + sb.Append("Number of data records: ").Append(this.dvbctChannelCount).AppendLine(); + sb.Append("Length of data record: ").Append(this.actChannelSize).AppendLine(); + sb.AppendLine(); + + sb.AppendLine(); + sb.AppendLine("DVB-S"); + if (satConfig != null) + { + int numberOfDupePrNr; + CountDuplicateRecords(out numberOfDupePrNr); + sb.Append("Max number of data records: ").Append(satConfig.dvbsMaxChannelCount).AppendLine(); + sb.Append("Length of data record: ").Append(satConfig.dvbsChannelLength).AppendLine(); + sb.Append("Channel records in use: ").Append(dvbsChannelCount).AppendLine(); + sb.Append("Channel records marked hard-deleted: ").Append(this.deletedChannelsHard).AppendLine(); + sb.Append("Channel records marked soft-deleted: ").Append(this.deletedChannelsSoft).AppendLine(); + sb.Append("Channel records erased (duplicates): ").Append(this.duplicateChannels).AppendLine(); + sb.Append("Channel records with Pr# 0: ").Append(dvbsChannelsAtPr0).AppendLine(); + sb.Append("Channel records with duplicate Pr#: ").Append(numberOfDupePrNr).AppendLine(); + } + else + sb.AppendLine("not present"); + + return sb.ToString(); + } + + private void CountDuplicateRecords(out int numberOfDupePrNr) + { + numberOfDupePrNr = 0; + foreach (var list in this.DataRoot.ChannelLists) + { + if ((list.SignalSource & SignalSource.Sat) != 0) + numberOfDupePrNr += list.DuplicateProgNrCount; + } + } + #endregion + + #region TvCountryCode + public string TvCountryCode + { + get { return this.countryCode; } + set + { + if (value.Length < 3 || this.settingsBlockOffset == 0 || this.settingsBlockSize < 8) return; + value = value.ToUpper(); + int off = this.settingsBlockOffset + 4 + 4 + 2; + for (int i = 0; i < 3; i++) + this.fileContent[off--] = (byte)value[i]; + this.countryCode = value; + } + } + #endregion + + #region ShowDeviceSettingsForm() + public override void ShowDeviceSettingsForm(object parentWindow) + { + using (var dlg = new TvSettingsForm(this)) + { + dlg.ShowDialog((Form)parentWindow); + } + } + #endregion + + #region GetFirmwareMapping() + public FirmwareData GetFirmwareMapping() + { + var mapping = this.firmwareMappings.GetMapping(this.firmwareBlockSize, false); + if (mapping == null) return null; + mapping.SetDataPtr(this.fileContent, this.firmwareBlockOffset); + return mapping; + } + #endregion + + // Testing + + #region GetHotelMenuOffset() + public int GetHotelMenuOffset() + { + int off = this.firmwareBlockOffset; + for (int i = 6500; i < this.FirmwareBlockSize - 3; i++) + { + if (BitConverter.ToUInt32(this.fileContent, off + i) == 0x05000101) // 1,1,0,5 + { + for (int j = 5; j < 20; j++) // backtrack to find Volume/MaxVolue pattern + { + if (fileContent[off + i - j] == 101 && fileContent[off + i - j - 6] == 100) + // check for Volume/MaxVolue to be 101/100 + return this.firmwareBlockOffset + i - j - 15; + } + return -1; + } + } + return -1; + } + #endregion + + internal int ACTChannelLength { get { return this.actChannelSize; } } + internal bool HasDvbs { get { return dvbsBlockOffset != 0; } } + internal int SatChannelLength { get { return satConfig != null ? satConfig.dvbsChannelLength : 0; } } + internal bool SatSymbolRateDiv2 { get { return this.isDvbsSymbolRateDiv2; } } + internal int FirmwareBlockSize { get { return this.firmwareBlockSize; } } + } +} diff --git a/ChanSort.Plugin.TllFile2/TllFileSerializerPlugin.cs b/ChanSort.Plugin.TllFile2/TllFileSerializerPlugin.cs new file mode 100644 index 0000000..b4853c8 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/TllFileSerializerPlugin.cs @@ -0,0 +1,27 @@ +using System.IO; +using ChanSort.Api; + +namespace ChanSort.Plugin.TllFile +{ + public class TllFileSerializerPlugin : ISerializerPlugin + { + private const int MAX_FILE_SIZE = 16*1000*1000; + private readonly string ERR_fileTooBig = Resource.TllFileSerializerPlugin_ERR_fileTooBig; + + + public string PluginName { get { return Resource.TllFileSerializerPlugin_PluginName; } } + public string FileFilter { get { return "*.TLL"; } } + + #region CreateSerializer() + public SerializerBase CreateSerializer(string inputFile) + { + long fileSize = new FileInfo(inputFile).Length; + if (fileSize > MAX_FILE_SIZE) + throw new IOException(string.Format(ERR_fileTooBig, fileSize, MAX_FILE_SIZE)); + + return new TllFileSerializer(inputFile); + } + #endregion + + } +} diff --git a/ChanSort.Plugin.TllFile2/TvSettingsForm.Designer.cs b/ChanSort.Plugin.TllFile2/TvSettingsForm.Designer.cs new file mode 100644 index 0000000..c61de4f --- /dev/null +++ b/ChanSort.Plugin.TllFile2/TvSettingsForm.Designer.cs @@ -0,0 +1,223 @@ +namespace ChanSort.Plugin.TllFile +{ + partial class TvSettingsForm + { + /// + /// Required designer variable. + /// + private System.ComponentModel.IContainer components = null; + + /// + /// Clean up any resources being used. + /// + /// true if managed resources should be disposed; otherwise, false. + protected override void Dispose(bool disposing) + { + if (disposing && (components != null)) + { + components.Dispose(); + } + base.Dispose(disposing); + } + + #region Windows Form Designer generated code + + /// + /// Required method for Designer support - do not modify + /// the contents of this method with the code editor. + /// + private void InitializeComponent() + { + System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(TvSettingsForm)); + this.grpSettings = new DevExpress.XtraEditors.GroupControl(); + this.cbHbbTv = new DevExpress.XtraEditors.CheckEdit(); + this.cbCustomCountry = new DevExpress.XtraEditors.CheckEdit(); + this.comboBoxEdit1 = new DevExpress.XtraEditors.ComboBoxEdit(); + this.labelControl1 = new DevExpress.XtraEditors.LabelControl(); + this.btnOk = new DevExpress.XtraEditors.SimpleButton(); + this.btnCancel = new DevExpress.XtraEditors.SimpleButton(); + this.grpHotelMode = new DevExpress.XtraEditors.GroupControl(); + this.labelControl3 = new DevExpress.XtraEditors.LabelControl(); + this.labelControl2 = new DevExpress.XtraEditors.LabelControl(); + this.cbDtvUpdate = new DevExpress.XtraEditors.CheckEdit(); + this.cbHotelMode = new DevExpress.XtraEditors.CheckEdit(); + this.cbAutoChannelUpdate = new DevExpress.XtraEditors.CheckEdit(); + this.groupControl1 = new DevExpress.XtraEditors.GroupControl(); + this.grpFirmwareNote = new DevExpress.XtraEditors.GroupControl(); + this.labelControl4 = new DevExpress.XtraEditors.LabelControl(); + ((System.ComponentModel.ISupportInitialize)(this.grpSettings)).BeginInit(); + this.grpSettings.SuspendLayout(); + ((System.ComponentModel.ISupportInitialize)(this.cbHbbTv.Properties)).BeginInit(); + ((System.ComponentModel.ISupportInitialize)(this.cbCustomCountry.Properties)).BeginInit(); + ((System.ComponentModel.ISupportInitialize)(this.comboBoxEdit1.Properties)).BeginInit(); + ((System.ComponentModel.ISupportInitialize)(this.grpHotelMode)).BeginInit(); + this.grpHotelMode.SuspendLayout(); + ((System.ComponentModel.ISupportInitialize)(this.cbDtvUpdate.Properties)).BeginInit(); + ((System.ComponentModel.ISupportInitialize)(this.cbHotelMode.Properties)).BeginInit(); + ((System.ComponentModel.ISupportInitialize)(this.cbAutoChannelUpdate.Properties)).BeginInit(); + ((System.ComponentModel.ISupportInitialize)(this.groupControl1)).BeginInit(); + this.groupControl1.SuspendLayout(); + ((System.ComponentModel.ISupportInitialize)(this.grpFirmwareNote)).BeginInit(); + this.grpFirmwareNote.SuspendLayout(); + this.SuspendLayout(); + // + // grpSettings + // + this.grpSettings.Controls.Add(this.cbHbbTv); + this.grpSettings.Controls.Add(this.cbCustomCountry); + this.grpSettings.Controls.Add(this.comboBoxEdit1); + this.grpSettings.Controls.Add(this.labelControl1); + resources.ApplyResources(this.grpSettings, "grpSettings"); + this.grpSettings.Name = "grpSettings"; + // + // cbHbbTv + // + resources.ApplyResources(this.cbHbbTv, "cbHbbTv"); + this.cbHbbTv.Name = "cbHbbTv"; + this.cbHbbTv.Properties.Caption = resources.GetString("cbHbbTv.Properties.Caption"); + // + // cbCustomCountry + // + resources.ApplyResources(this.cbCustomCountry, "cbCustomCountry"); + this.cbCustomCountry.Name = "cbCustomCountry"; + this.cbCustomCountry.Properties.Caption = resources.GetString("cbCustomCountry.Properties.Caption"); + this.cbCustomCountry.CheckedChanged += new System.EventHandler(this.cbCustomCountry_CheckedChanged); + // + // comboBoxEdit1 + // + resources.ApplyResources(this.comboBoxEdit1, "comboBoxEdit1"); + this.comboBoxEdit1.Name = "comboBoxEdit1"; + this.comboBoxEdit1.Properties.Buttons.AddRange(new DevExpress.XtraEditors.Controls.EditorButton[] { + new DevExpress.XtraEditors.Controls.EditorButton(((DevExpress.XtraEditors.Controls.ButtonPredefines)(resources.GetObject("comboBoxEdit1.Properties.Buttons"))))}); + this.comboBoxEdit1.Properties.TextEditStyle = DevExpress.XtraEditors.Controls.TextEditStyles.DisableTextEditor; + // + // labelControl1 + // + resources.ApplyResources(this.labelControl1, "labelControl1"); + this.labelControl1.Name = "labelControl1"; + // + // btnOk + // + resources.ApplyResources(this.btnOk, "btnOk"); + this.btnOk.DialogResult = System.Windows.Forms.DialogResult.OK; + this.btnOk.Name = "btnOk"; + this.btnOk.Click += new System.EventHandler(this.btnOk_Click); + // + // btnCancel + // + resources.ApplyResources(this.btnCancel, "btnCancel"); + this.btnCancel.DialogResult = System.Windows.Forms.DialogResult.Cancel; + this.btnCancel.Name = "btnCancel"; + // + // grpHotelMode + // + this.grpHotelMode.Controls.Add(this.labelControl3); + this.grpHotelMode.Controls.Add(this.labelControl2); + this.grpHotelMode.Controls.Add(this.cbDtvUpdate); + this.grpHotelMode.Controls.Add(this.cbHotelMode); + resources.ApplyResources(this.grpHotelMode, "grpHotelMode"); + this.grpHotelMode.Name = "grpHotelMode"; + // + // labelControl3 + // + resources.ApplyResources(this.labelControl3, "labelControl3"); + this.labelControl3.Name = "labelControl3"; + // + // labelControl2 + // + resources.ApplyResources(this.labelControl2, "labelControl2"); + this.labelControl2.Name = "labelControl2"; + // + // cbDtvUpdate + // + resources.ApplyResources(this.cbDtvUpdate, "cbDtvUpdate"); + this.cbDtvUpdate.Name = "cbDtvUpdate"; + this.cbDtvUpdate.Properties.Caption = resources.GetString("cbDtvUpdate.Properties.Caption"); + // + // cbHotelMode + // + resources.ApplyResources(this.cbHotelMode, "cbHotelMode"); + this.cbHotelMode.Name = "cbHotelMode"; + this.cbHotelMode.Properties.Caption = resources.GetString("cbHotelMode.Properties.Caption"); + // + // cbAutoChannelUpdate + // + resources.ApplyResources(this.cbAutoChannelUpdate, "cbAutoChannelUpdate"); + this.cbAutoChannelUpdate.Name = "cbAutoChannelUpdate"; + this.cbAutoChannelUpdate.Properties.Caption = resources.GetString("cbAutoChannelUpdate.Properties.Caption"); + // + // groupControl1 + // + this.groupControl1.Controls.Add(this.cbAutoChannelUpdate); + resources.ApplyResources(this.groupControl1, "groupControl1"); + this.groupControl1.Name = "groupControl1"; + // + // grpFirmwareNote + // + this.grpFirmwareNote.Controls.Add(this.labelControl4); + resources.ApplyResources(this.grpFirmwareNote, "grpFirmwareNote"); + this.grpFirmwareNote.Name = "grpFirmwareNote"; + // + // labelControl4 + // + resources.ApplyResources(this.labelControl4, "labelControl4"); + this.labelControl4.Name = "labelControl4"; + // + // TvSettingsForm + // + this.AcceptButton = this.btnOk; + this.Appearance.Options.UseBackColor = true; + resources.ApplyResources(this, "$this"); + this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; + this.CancelButton = this.btnCancel; + this.Controls.Add(this.grpHotelMode); + this.Controls.Add(this.btnCancel); + this.Controls.Add(this.btnOk); + this.Controls.Add(this.grpSettings); + this.Controls.Add(this.groupControl1); + this.Controls.Add(this.grpFirmwareNote); + this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedDialog; + this.MaximizeBox = false; + this.MinimizeBox = false; + this.Name = "TvSettingsForm"; + this.Load += new System.EventHandler(this.TvSettingsForm_Load); + ((System.ComponentModel.ISupportInitialize)(this.grpSettings)).EndInit(); + this.grpSettings.ResumeLayout(false); + this.grpSettings.PerformLayout(); + ((System.ComponentModel.ISupportInitialize)(this.cbHbbTv.Properties)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.cbCustomCountry.Properties)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.comboBoxEdit1.Properties)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.grpHotelMode)).EndInit(); + this.grpHotelMode.ResumeLayout(false); + this.grpHotelMode.PerformLayout(); + ((System.ComponentModel.ISupportInitialize)(this.cbDtvUpdate.Properties)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.cbHotelMode.Properties)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.cbAutoChannelUpdate.Properties)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.groupControl1)).EndInit(); + this.groupControl1.ResumeLayout(false); + ((System.ComponentModel.ISupportInitialize)(this.grpFirmwareNote)).EndInit(); + this.grpFirmwareNote.ResumeLayout(false); + this.ResumeLayout(false); + + } + + #endregion + + private DevExpress.XtraEditors.GroupControl grpSettings; + private DevExpress.XtraEditors.ComboBoxEdit comboBoxEdit1; + private DevExpress.XtraEditors.LabelControl labelControl1; + private DevExpress.XtraEditors.SimpleButton btnOk; + private DevExpress.XtraEditors.SimpleButton btnCancel; + private DevExpress.XtraEditors.CheckEdit cbCustomCountry; + private DevExpress.XtraEditors.GroupControl grpHotelMode; + private DevExpress.XtraEditors.CheckEdit cbHbbTv; + private DevExpress.XtraEditors.CheckEdit cbDtvUpdate; + private DevExpress.XtraEditors.CheckEdit cbHotelMode; + private DevExpress.XtraEditors.CheckEdit cbAutoChannelUpdate; + private DevExpress.XtraEditors.GroupControl groupControl1; + private DevExpress.XtraEditors.LabelControl labelControl3; + private DevExpress.XtraEditors.LabelControl labelControl2; + private DevExpress.XtraEditors.GroupControl grpFirmwareNote; + private DevExpress.XtraEditors.LabelControl labelControl4; + } +} \ No newline at end of file diff --git a/ChanSort.Plugin.TllFile2/TvSettingsForm.cs b/ChanSort.Plugin.TllFile2/TvSettingsForm.cs new file mode 100644 index 0000000..7bf7cfc --- /dev/null +++ b/ChanSort.Plugin.TllFile2/TvSettingsForm.cs @@ -0,0 +1,65 @@ +using System; +using DevExpress.XtraEditors; +using DevExpress.XtraEditors.Controls; + +namespace ChanSort.Plugin.TllFile +{ + public partial class TvSettingsForm : XtraForm + { + private readonly TllFileSerializer tvSerializer; + + public TvSettingsForm(TllFileSerializer tvSerializer) + { + this.tvSerializer = tvSerializer; + InitializeComponent(); + } + + private void TvSettingsForm_Load(object sender, EventArgs e) + { + var items = tvSerializer.SupportedTvCountryCodes; + foreach(var item in items) + this.comboBoxEdit1.Properties.Items.Add(item); + this.comboBoxEdit1.Text = this.tvSerializer.TvCountryCode; + + var mapping = this.tvSerializer.GetFirmwareMapping(); + if (mapping != null) + { + this.cbAutoChannelUpdate.Checked = mapping.SettingsAutomaticChannelUpdate; + this.cbHbbTv.Checked = mapping.HbbTvEnabled; + this.cbHotelMode.Checked = mapping.HotelModeEnabled; + this.cbDtvUpdate.Checked = mapping.HotelModeDtvUpdate; + + this.grpFirmwareNote.Visible = false; + this.Height -= this.grpFirmwareNote.Height; + } + else + { + this.cbAutoChannelUpdate.Enabled = false; + this.cbHbbTv.Enabled = false; + this.cbHotelMode.Enabled = false; + this.cbDtvUpdate.Enabled = false; + } + } + + private void btnOk_Click(object sender, EventArgs e) + { + this.tvSerializer.TvCountryCode = this.comboBoxEdit1.Text; + + var mapping = this.tvSerializer.GetFirmwareMapping(); + if (mapping != null) + { + mapping.SettingsAutomaticChannelUpdate = this.cbAutoChannelUpdate.Checked; + mapping.HbbTvEnabled = this.cbHbbTv.Checked; + mapping.HotelModeEnabled = this.cbHotelMode.Checked; + mapping.HotelModeDtvUpdate = this.cbDtvUpdate.Checked; + } + } + + private void cbCustomCountry_CheckedChanged(object sender, EventArgs e) + { + this.comboBoxEdit1.Properties.TextEditStyle = this.cbCustomCountry.Checked + ? TextEditStyles.Standard + : TextEditStyles.DisableTextEditor; + } + } +} diff --git a/ChanSort.Plugin.TllFile2/TvSettingsForm.de.resx b/ChanSort.Plugin.TllFile2/TvSettingsForm.de.resx new file mode 100644 index 0000000..7cbedf2 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/TvSettingsForm.de.resx @@ -0,0 +1,325 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + + + + + + + + + True + + + HbbTV aktivieren (funktioniert nur mit den Ländereinstellungen DEU, FRA, NED und ESP) + + + + + + + + + + + + + + + + + + True + + + Eigene Werte erlauben (auf eigene Gefahr!) + + + + + + + + + + + + + + + + + + True + + + + + + False + + + + 27, 13 + + + Land: + + + OPTION Menü + + + Abbrechen + + + HINWEIS: Bei aktivem Hotel-Modus kann man in der EPG nicht zum gewählten Sender wechseln und die Funktion "Werkseinstellungen" ist gesperrt. + + + 341, 13 + + + Die folgenden Einstellungen funktionieren nur bei aktivem Hotel-Modus: + + + + + + + + + True + + + D-TV Senderliste automatisch aktualisieren (empfohlen: AUS) + + + + + + + + + + + + + + + + + + True + + + Hotel Modus aktivieren (empfohlen: EIN) + + + + + + + + + + + + Hotel Modus + + + + + + + + + True + + + Senderliste automatisch aktualisieren (empfohlen: AUS) + + + + + + + + + + + + EINST. Menü + + + Das Dateiformat Ihres TV-Modells wird nicht vollständig unterstützt. Deshalb sind viele Einstellungen in diesem Dialog gesperrt. + + + + + + + + + True + + + + Default + + + False + + + + + + True + + + None + + + _ + + + True + + + True + + + False + + + + + + False + + + Horizontal + + + + + + TV Einstellungen + + \ No newline at end of file diff --git a/ChanSort.Plugin.TllFile2/TvSettingsForm.resx b/ChanSort.Plugin.TllFile2/TvSettingsForm.resx new file mode 100644 index 0000000..e459046 --- /dev/null +++ b/ChanSort.Plugin.TllFile2/TvSettingsForm.resx @@ -0,0 +1,569 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + + Top, Left, Right + + + + 12, 64 + + + Enable HbbTV (only works with country settings DEU, FRA, NED and ESP) + + + 456, 19 + + + + 3 + + + cbHbbTv + + + DevExpress.XtraEditors.CheckEdit, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpSettings + + + 0 + + + Top, Left, Right + + + 150, 30 + + + allow custom value (at your own risk!) + + + 320, 19 + + + 2 + + + cbCustomCountry + + + DevExpress.XtraEditors.CheckEdit, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpSettings + + + 1 + + + 72, 29 + + + + Combo + + + 72, 20 + + + 1 + + + comboBoxEdit1 + + + DevExpress.XtraEditors.ComboBoxEdit, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpSettings + + + 2 + + + 12, 32 + + + 43, 13 + + + 0 + + + Country: + + + labelControl1 + + + DevExpress.XtraEditors.LabelControl, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpSettings + + + 3 + + + Top + + + 0, 142 + + + 480, 106 + + + 0 + + + OPTION Menu + + + grpSettings + + + DevExpress.XtraEditors.GroupControl, DevExpress.Utils.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + $this + + + 3 + + + Bottom, Right + + + 310, 413 + + + 75, 23 + + + 1 + + + Ok + + + btnOk + + + DevExpress.XtraEditors.SimpleButton, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + $this + + + 2 + + + Bottom, Right + + + 395, 413 + + + 75, 23 + + + 2 + + + Cancel + + + btnCancel + + + DevExpress.XtraEditors.SimpleButton, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + $this + + + 1 + + + + Vertical + + + 12, 26 + + + 458, 26 + + + 7 + + + NOTE: When Hotel Mode is active, you can no longer activate a channel from inside the EPG and the "Factory Reset" function becomes disabled. + + + labelControl3 + + + DevExpress.XtraEditors.LabelControl, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpHotelMode + + + 0 + + + 41, 93 + + + 315, 13 + + + 6 + + + The settings below are only effective when Hotel Mode is enabled + + + labelControl2 + + + DevExpress.XtraEditors.LabelControl, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpHotelMode + + + 1 + + + Top, Left, Right + + + 39, 112 + + + Automatic D-TV channel update (recommended: OFF) + + + 431, 19 + + + 5 + + + cbDtvUpdate + + + DevExpress.XtraEditors.CheckEdit, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpHotelMode + + + 2 + + + Top, Left, Right + + + 10, 58 + + + Enable Hotel Mode (recommended: ON) + + + 456, 19 + + + 4 + + + cbHotelMode + + + DevExpress.XtraEditors.CheckEdit, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpHotelMode + + + 3 + + + Top + + + 0, 248 + + + 480, 151 + + + 3 + + + Hotel Mode + + + grpHotelMode + + + DevExpress.XtraEditors.GroupControl, DevExpress.Utils.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + $this + + + 0 + + + Top, Left, Right + + + 12, 35 + + + Automatic Channel Update (recommended: OFF) + + + 456, 19 + + + 3 + + + cbAutoChannelUpdate + + + DevExpress.XtraEditors.CheckEdit, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + groupControl1 + + + 0 + + + Top + + + 0, 71 + + + 480, 71 + + + 5 + + + SETUP Menu + + + groupControl1 + + + DevExpress.XtraEditors.GroupControl, DevExpress.Utils.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + $this + + + 4 + + + Vertical + + + 11, 29 + + + 458, 26 + + + 8 + + + Your TV model's TLL file format is not fully supported. Therefore many features in this dialog are disabled. + + + labelControl4 + + + DevExpress.XtraEditors.LabelControl, DevExpress.XtraEditors.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + grpFirmwareNote + + + 0 + + + Top + + + 0, 0 + + + 480, 71 + + + 6 + + + Information + + + grpFirmwareNote + + + DevExpress.XtraEditors.GroupControl, DevExpress.Utils.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + + $this + + + 5 + + + True + + + 6, 13 + + + 480, 448 + + + CenterParent + + + TV Settings + + + TvSettingsForm + + + DevExpress.XtraEditors.XtraForm, DevExpress.Utils.v12.2, Version=12.2.6.0, Culture=neutral, PublicKeyToken=b88d1754d700e49a + + \ No newline at end of file diff --git a/ChanSort.Ui/AboutForm.cs b/ChanSort.Ui/AboutForm.cs index 56abe75..2117fe1 100644 --- a/ChanSort.Ui/AboutForm.cs +++ b/ChanSort.Ui/AboutForm.cs @@ -29,7 +29,7 @@ For providing example TLL files, error feedback and other helpful information"; private void gvPlugins_CustomUnboundColumnData(object sender, DevExpress.XtraGrid.Views.Base.CustomColumnDataEventArgs e) { if (e.Column == this.colPlugin) - e.Value = (Path.GetFileName(e.Row.GetType().Assembly.Location) ?? "").Replace("ChanSort.Plugin.", ""); + e.Value = (Path.GetFileName(e.Row.GetType().Assembly.Location) ?? "").Replace("ChanSort.Loader.", ""); } private void picDonate_Click(object sender, System.EventArgs e) diff --git a/ChanSort.Ui/ChanSort.Ui.csproj b/ChanSort.Ui/ChanSort.csproj similarity index 100% rename from ChanSort.Ui/ChanSort.Ui.csproj rename to ChanSort.Ui/ChanSort.csproj diff --git a/ChanSort.Ui/MainForm.cs b/ChanSort.Ui/MainForm.cs index 286fdc3..9447276 100644 --- a/ChanSort.Ui/MainForm.cs +++ b/ChanSort.Ui/MainForm.cs @@ -68,6 +68,7 @@ namespace ChanSort.Ui this.grpOutputList.BindingContext = bcLeft; this.lastFocusedGrid = this.gviewInput; this.comboEditMode.SelectedIndex = (int) this.curEditMode; + this.comboUnsortedAction.SelectedIndex = (int)UnsortedChannelMode.Hide; this.ActiveControl = this.gridInput; } #endregion @@ -94,7 +95,7 @@ namespace ChanSort.Ui { var list = new List(); string exeDir = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location); - foreach (var file in Directory.GetFiles(exeDir, "ChanSort.Plugin.*.dll")) + foreach (var file in Directory.GetFiles(exeDir, "ChanSort.Loader.*.dll")) { try { @@ -185,7 +186,7 @@ namespace ChanSort.Ui this.currentPlugin = plugin; this.currentTvSerializer = newSerializer; this.currentTvSerializer.DefaultEncoding = this.defaultEncoding; - this.btnResetChannelData.Visible = newSerializer.SupportsEraseChannelData; + this.btnResetChannelData.Visible = newSerializer.Features.EraseChannelData; if (!this.LoadTvDataFile()) return; this.LoadCsvFile(); @@ -204,8 +205,8 @@ namespace ChanSort.Ui this.SetControlsEnabled(!this.dataRoot.IsEmpty); this.UpdateFavoritesEditor(this.dataRoot.SupportedFavorites); - this.colName.OptionsColumn.AllowEdit = this.currentTvSerializer.SupportsChannelNameEdit; - this.colOutName.OptionsColumn.AllowEdit = this.currentTvSerializer.SupportsChannelNameEdit; + this.colName.OptionsColumn.AllowEdit = this.currentTvSerializer.Features.ChannelNameEdit; + this.colOutName.OptionsColumn.AllowEdit = this.currentTvSerializer.Features.ChannelNameEdit; if (this.dataRoot.Warnings.Length > 0) { @@ -432,6 +433,7 @@ namespace ChanSort.Ui { this.gviewInput.BeginDataUpdate(); this.gviewOutput.BeginDataUpdate(); + this.editor.AutoNumberingForUnassignedChannels((UnsortedChannelMode)this.comboUnsortedAction.SelectedIndex); this.SaveReferenceFile(); this.SaveTvDataFile(); this.dataRoot.NeedsSaving = false; @@ -476,7 +478,7 @@ namespace ChanSort.Ui if (!File.Exists(bakFile)) File.Copy(currentTvFile, bakFile); } - this.currentTvSerializer.Save(this.currentTvFile, this.currentCsvFile, (UnsortedChannelMode)this.comboUnsortedAction.SelectedIndex); + this.currentTvSerializer.Save(this.currentTvFile, this.currentCsvFile); } finally { diff --git a/ChanSort.sln b/ChanSort.sln index 45f19d3..8aae224 100644 --- a/ChanSort.sln +++ b/ChanSort.sln @@ -1,7 +1,7 @@  Microsoft Visual Studio Solution File, Format Version 11.00 # Visual Studio 2010 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort.Ui", "ChanSort.Ui\ChanSort.Ui.csproj", "{5FAFDABC-A52F-498C-BD2F-AFFC4119797A}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort", "ChanSort.Ui\ChanSort.csproj", "{5FAFDABC-A52F-498C-BD2F-AFFC4119797A}" ProjectSection(ProjectDependencies) = postProject {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5} = {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5} {E972D8A1-2F5F-421C-AC91-CFF45E5191BE} = {E972D8A1-2F5F-421C-AC91-CFF45E5191BE} @@ -9,42 +9,63 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort.Ui", "ChanSort.Ui\ EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort.Api", "ChanSort.Api\ChanSort.Api.csproj", "{DCCFFA08-472B-4D17-BB90-8F513FC01392}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort.Plugin.TllFile", "ChanSort.Plugin.TllFile\ChanSort.Plugin.TllFile.csproj", "{E972D8A1-2F5F-421C-AC91-CFF45E5191BE}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort.Loader.TllFile", "ChanSort.Plugin.TllFile\ChanSort.Loader.TllFile.csproj", "{E972D8A1-2F5F-421C-AC91-CFF45E5191BE}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{67AED502-8AEB-45F2-9B95-AC42B6A5D2C4}" ProjectSection(SolutionItems) = preProject - FileFormat.docx = FileFormat.docx readme.txt = readme.txt EndProjectSection EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Test.Plugin.TllFile", "Test.Plugin.TllFile\Test.Plugin.TllFile.csproj", "{68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Test.Loader.TllFile", "Test.Plugin.TllFile\Test.Loader.TllFile.csproj", "{68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort.Plugin.ScmFile", "ChanSort.Plugin.ScmFile\ChanSort.Plugin.ScmFile.csproj", "{A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChanSort.Loader.ScmFile", "ChanSort.Plugin.ScmFile\ChanSort.Loader.ScmFile.csproj", "{A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}" EndProject Global GlobalSection(TestCaseManagementSettings) = postSolution CategoryFile = ChanSort1.vsmdi EndGlobalSection GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Any CPU = Debug|Any CPU Debug|x86 = Debug|x86 + Release|Any CPU = Release|Any CPU Release|x86 = Release|x86 EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution + {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Debug|Any CPU.Build.0 = Debug|Any CPU {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Debug|x86.ActiveCfg = Debug|x86 {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Debug|x86.Build.0 = Debug|x86 + {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Release|Any CPU.ActiveCfg = Release|Any CPU + {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Release|Any CPU.Build.0 = Release|Any CPU {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Release|x86.ActiveCfg = Release|x86 {5FAFDABC-A52F-498C-BD2F-AFFC4119797A}.Release|x86.Build.0 = Release|x86 + {DCCFFA08-472B-4D17-BB90-8F513FC01392}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {DCCFFA08-472B-4D17-BB90-8F513FC01392}.Debug|Any CPU.Build.0 = Debug|Any CPU {DCCFFA08-472B-4D17-BB90-8F513FC01392}.Debug|x86.ActiveCfg = Debug|x86 {DCCFFA08-472B-4D17-BB90-8F513FC01392}.Debug|x86.Build.0 = Debug|x86 + {DCCFFA08-472B-4D17-BB90-8F513FC01392}.Release|Any CPU.ActiveCfg = Release|Any CPU + {DCCFFA08-472B-4D17-BB90-8F513FC01392}.Release|Any CPU.Build.0 = Release|Any CPU {DCCFFA08-472B-4D17-BB90-8F513FC01392}.Release|x86.ActiveCfg = Release|Any CPU + {E972D8A1-2F5F-421C-AC91-CFF45E5191BE}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {E972D8A1-2F5F-421C-AC91-CFF45E5191BE}.Debug|Any CPU.Build.0 = Debug|Any CPU {E972D8A1-2F5F-421C-AC91-CFF45E5191BE}.Debug|x86.ActiveCfg = Debug|x86 {E972D8A1-2F5F-421C-AC91-CFF45E5191BE}.Debug|x86.Build.0 = Debug|x86 + {E972D8A1-2F5F-421C-AC91-CFF45E5191BE}.Release|Any CPU.ActiveCfg = Release|Any CPU + {E972D8A1-2F5F-421C-AC91-CFF45E5191BE}.Release|Any CPU.Build.0 = Release|Any CPU {E972D8A1-2F5F-421C-AC91-CFF45E5191BE}.Release|x86.ActiveCfg = Release|Any CPU + {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}.Debug|Any CPU.Build.0 = Debug|Any CPU {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}.Debug|x86.ActiveCfg = Debug|x86 {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}.Debug|x86.Build.0 = Debug|x86 + {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}.Release|Any CPU.ActiveCfg = Release|Any CPU + {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}.Release|Any CPU.Build.0 = Release|Any CPU {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2}.Release|x86.ActiveCfg = Release|Any CPU + {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}.Debug|Any CPU.Build.0 = Debug|Any CPU {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}.Debug|x86.ActiveCfg = Debug|x86 {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}.Debug|x86.Build.0 = Debug|x86 + {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}.Release|Any CPU.ActiveCfg = Release|Any CPU + {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}.Release|Any CPU.Build.0 = Release|Any CPU {A1C9A98D-368A-44E8-9B7F-7EACA46C9EC5}.Release|x86.ActiveCfg = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution diff --git a/Source.7z b/Source.7z new file mode 100644 index 0000000..774a74e Binary files /dev/null and b/Source.7z differ diff --git a/Test.Plugin.TllFile/Test.Plugin.TllFile.csproj b/Test.Plugin.TllFile/Test.Loader.TllFile.csproj similarity index 95% rename from Test.Plugin.TllFile/Test.Plugin.TllFile.csproj rename to Test.Plugin.TllFile/Test.Loader.TllFile.csproj index e53d418..ef1cafb 100644 --- a/Test.Plugin.TllFile/Test.Plugin.TllFile.csproj +++ b/Test.Plugin.TllFile/Test.Loader.TllFile.csproj @@ -9,8 +9,8 @@ {68CFCB2F-B52A-43A1-AA5C-5D64A1D655D2} Library Properties - Test.Plugin.TllFile - Test.Plugin.TllFile + Test.Loader.TllFile + Test.Loader.TllFile v3.5 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} @@ -76,10 +76,9 @@ ChanSort.Api True - + {E972D8A1-2F5F-421C-AC91-CFF45E5191BE} - ChanSort.Plugin.TllFile - True + ChanSort.Loader.TllFile diff --git a/Test.Plugin.TllFile/UnitTest1.cs b/Test.Plugin.TllFile/UnitTest1.cs index 67270ec..a6bc7e6 100644 --- a/Test.Plugin.TllFile/UnitTest1.cs +++ b/Test.Plugin.TllFile/UnitTest1.cs @@ -5,10 +5,10 @@ using System.IO; using System.Linq; using System.Reflection; using System.Text; -using ChanSort.Plugin.TllFile; +using ChanSort.Loader.TllFile; using Microsoft.VisualStudio.TestTools.UnitTesting; -namespace Test.Plugin.TllFile +namespace Test.Loader.TllFile { [TestClass] public class UnitTest1 @@ -52,10 +52,10 @@ namespace Test.Plugin.TllFile new ExpectedData(@"FranzSteinert\xxCS460S-ZA00001.TLL", 0, 0, 1261, 0, 200), // ?/68 new ExpectedData(@"Klausi1\xxLK950S-ZA00001.TLL", 37, 390, 2695, 150, 491), // 184/68 new ExpectedData(@"MP3Chris2712\xxLV570S-ZB00001.TLL", 0, 12, 2895, 0, 669), // 184/68 - new ExpectedData(@"decklen\xxLW570S-ZD00001.TLL", 0, 30, 1587, 0, 339), // 184/68 + new ExpectedData(@"decklen\xxLW570S-ZD00001.TLL", 0, 30, 1598, 0, 339), // 184/68 new ExpectedData(@"NeuerScan\xxLM340S-ZA00001.TLL", 34, 317, 1698, 129, 264), // 188/68 new ExpectedData(@"wagnale\xxLM611S-ZA00001.TLL", 0, 13, 1094, 0, 191), // 188/68 - new ExpectedData(@"_Pred\xxLM620S-ZE00021.TLL", 0, 11, 1302, 0, 191), // 192/72 + new ExpectedData(@"_Pred\xxLM620S-ZE00021.TLL", 0, 11, 1303, 0, 191), // 192/72 }; foreach (var entry in expected) @@ -70,7 +70,8 @@ namespace Test.Plugin.TllFile #region TestLoadingAllTllFilesInTestFilesDirectory() [TestMethod] - [DeploymentItem("ChanSort.Plugin.TllFile\\ChanSort.Plugin.TllFile.ini")] + [DeploymentItem("ChanSort.Loader.TllFile\\ChanSort.Loader.TllFile.ini")] + [DeploymentItem("ChanSort.Loader.TllFile2\\ChanSort.Loader.TllFile2.ini")] public void TestLoadingAllTllFilesInTestFilesDirectory() { TllFileSerializerPlugin plugin = new TllFileSerializerPlugin(); @@ -78,10 +79,10 @@ namespace Test.Plugin.TllFile StringBuilder errors = new StringBuilder(); var list = this.FindAllTllFiles(); var models = new Dictionary(); - var firmwareSize = new Dictionary(); + var firmwareSize = new Dictionary(); foreach(var file in list) { - if (file.Contains("GlobalClone")) + if (file.Contains("GlobalClone") || file.Contains("CountrySettings")) continue; Debug.Print("Testing " + file); try @@ -103,14 +104,14 @@ namespace Test.Plugin.TllFile models[key] = relPath; var model = this.GetModel(file); - if (firmwareSize.ContainsKey(serializer.FirmwareDataLength)) + if (firmwareSize.ContainsKey(serializer.FirmwareBlockSize)) { - string x = firmwareSize[serializer.FirmwareDataLength]; + string x = firmwareSize[serializer.FirmwareBlockSize]; if (!x.Contains(model)) - firmwareSize[serializer.FirmwareDataLength] = x + ", " + model; + firmwareSize[serializer.FirmwareBlockSize] = x + ", " + model; } else - firmwareSize[serializer.FirmwareDataLength] = model; + firmwareSize[serializer.FirmwareBlockSize] = model;