akardam.net Motorola Tools & Documents - CPS Out of Band Modification HOW-TO « return to akardam.net
« Return to Tools & Documents
« Return to Documents & HOW-TOs

CPS Out of Band Modification HOW-TO
v2.0 03/17/2012

Introduction

This document details how to make modifications to currently available Customer Programming Software (CPS) for the Motorola Astro and Astro25 series tranceivers, to allow out of band programming. Modification methods discussed herein may be applicable to other CPS packages; the reader is encouraged to experiment on their own.

The Basics

Out of band (OOB) programming is the process of programming a frequency into a radio outside of its rated bandsplit. For example, Astro25 portables (such as the XTS5000) in the upper UHF split (which is called the UHF Range 2, or S split), have a rated bandsplit of 450-520. However, each physical RF component has slightly different tolerances, and may operate within specification (power output, frequency stability, etc) up to several MHz outside of the rated bandsplit. CPS will in some few cases (depending on band, model, etc) allow such programming without modification. In all other cases, it is necessary to modify CPS to allow such frequencies to be programmed without error.

Notice & Disclaimer

This guide is intended to allow Motorola enthusiasts to operate a radio tranceiver in a modified condition, on frequencies for which FCC type acceptance is not required (for example, on the amateur radio bands). A radio tranceiver modified thusly should not be used for commercial or public safety service, or in any situation where communications are critical or convey life and safety information.

The author(s) of this work hereby disclaim that the information given herein is suitable for any purpose whatsoever, and do not make any warranties or guaruntees, either implied or expressed, of the suitability of the information for any purpose. The author(s) of this work disclaim all liability in the event that the use of the information given herein results in harm to persons or property, to any extent.

Important: Please remember to make a backup of any executable file you modify before you begin. Make sure also to make backups of any codeplug on which you intend to use modified CPS. It would probably be a good idea to rigorously test any modified CPS on a test codeplug (to guard against inadvertent modification of non-bandsplit edge value data) prior to reading from or writing to any radios.


Section 1: History & Notes

This HOW-TO is based on the original WinCPS OOB document located at Batlabs.

Reference Band Edge Tables

For each CPS package (Portable and Mobile) there are generally two sets of band edges for each bandsplit, one for the bandsplit lower edge and one for the bandsplit upper edge. The table below shows the band tables for the Astro CPS packages, as presented on Batlabs. There is band info for various VHF, UHF, and 800 splits, which is generally represented in integer MHz values (except for the VHF value of 162.550):

Table 1: Astro Bandsplit Edge Table (Batlabs)

Astro Mobile Astro Portable
Lower Band Edge Tables
136 403 450 830 136 146 136 136 403 438 450 453 433

136 403 445 830 133 142 136 136 403 438 440 453 475

136 403 450 825 136 146 136 136 403 438 450 450 482

136 403 450 830 136 146 136 136 403 438 450 453 482

136 403 445 830 133 142 136 136 403 438 440 453 475
136 403 450 830 136 146 136 136 403 438 450 453 482

136 403 445 830 133 142 136 136 403 438 440 453 475

136 403 450 825 136 146 136 136 403 438 450 450 482

136 403 450 830 136 146 136 136 403 438 450 453 482

136 403 445 830 133 142 136 136 403 438 440 453 475
Upper Band Edge Tables
178 470 520 915 162 174 174 174 433 470 482 490 512

179 477 521 915 171 175 174 174 441 470 491 490 515
178 470 520 915 162 174 174 174 433 470 482 490 512

179 477 521 915 171 175 174 174 441 470 491 490 515



Section 2: Current CPS Bandsplit Edge Discussion

Throughout this section, we will be using examples derived from Astro25 Portable CPS R09.01.02

Please Note: This document assumes that the reader has some basic knowledge of the tools mentioned, such as hex editors and debugging tools. Advanced topics, such as decompilation, are beyond the scope of this document.

In order to understand how bandsplit edge values are modified, it is first necessary to understand the basics of how the CPS executable functions. Astro and Astro25 CPS executables are what are known as Windows Portable Executable files. Such files are comprised of one or more sections of raw information, which can contain executable code, data, Win32 Resource objects, etc. The sections are defined by the section table, which immediately follows the PE header at the beginning of the file.

It is important to understand that these sections exist, because they in part define how we go about searching for bandsplit edge values (and collections of values in tables). Classically, bandsplit edge values were defined strictly in PE sections that contained only data (do not contain executable code). However, as time has progressed, it appears that some values that pertain to what frequency ranges the radio is allowed to operate in are being placed in sections of executable code. This seems to be especially prevalent for radios that operate on the 700 MHz band (more on this below). Thus, one might find a situation in which modifying bandsplit edge values in strictly data sections of the file do now allow certain OOB frequencies to be input, and in such situations additional values might need to be found and modified elsewhere within the CPS executable.

A useful tool to examine the contents of an executable file is a debugger. One of the better debuggers for Windows (and Windows executables) is OllyDbg. This kind of debugger will attempt to analyze the raw information in the executable file, determine which parts are executable code, and which are strictly data. A very useful and essential accompanyment to a debugger is the document that defines the the processor's instruction set. In the case of Astro and Astro25 CPS, this is the Intel x86 instruction set, reference material for which may be found on Intel's website.

To date, all Astro and Astro25 CPS executables examined have had four PE sections, as follows:

Table 2: Example CPS executable PE Section Table

Section #NameOffsetSize
01.text0x000010000x00D88000
02.rdata0x00D890000x0013A000
03.data0x00EC30000x00503000
04.rsrc0x013C6000x001FA000


In this case the ".rdata" and ".data" sections contain raw data, and the ".rsrc" section contains Win32 Resource Objects (such as program icons, dialog boxes, etc). The ".text" section contains the executable code, and is the largest of the sections. If you load up the executable in OllyDbg, this should be the only section that shows up as executable module memory.


Section 2a: Bandsplit Edge Values in PE data-only sections

Before we look at where and how we find the actual bandsplit edge values, let's look at the layout of the tables.

Each table is comprised of a number of columns and rows. Astro CPS uses a table with 18 columns, and Astro25 CPS uses a table with 20 columns. Below is a meta-table showing a general description of each column and what that column is used for in the CPS packages of each platform.

Table 3: Overview of primary CPS Bandsplit Edge Tables

Col # 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
Band 800
Gen
900
Gen
Not
Used
VHF
Wide
UHF R1
Wide
UHF R2
Wide
800
Unk
VHF R1
Narrow
VHF R2
Narrow
VHF R3
Narrow
VHF R4
Narrow
UHF R1
Narrow
UHF R2
Narrow
UHF R3
Narrow
UHF 3.5
Narrow
UHF R4
Narrow
Not
Used
Not
Used
7/800
Gen
UHF R3.5
SP
Astro
CPS
800
Gen
900
Gen
Not
Used
Portable
VHF
K-Split
Portable
UHF R1
R-Split
Portable
UHF R2
S-Split
Unk Mobile
VHF R1
J-Split
Mobile
VHF R2
K-Split
Mobile
VHF R3
Unused
Mobile
VHF R3
Unused
Mobile
UHF R1
Q-Split
Mobile
UHF R2
R-Split
Mobile
UHF R3
R-Split
Mobile
UHF R3.5
R-Split
Mobile
UHF R4
S-Split
Not
Used
Not
Used
N/A N/A
Astro25
CPS
800
Gen
900
Gen
Not
Used
XTS/L
VHF
K-Split
XTS/L
UHF R1
Q-Split
XTS/L
UHF R2
S-Split
Unk AS+
VHF R1
J-Split
AS+
VHF R2
K-Split
AS+
VHF R3
Unused
AS+
VHF R3
Unused
AS+
UHF R1
Q-Split
AS+
UHF R2
R-Split
AS+
UHF R3
R-Split
AS+
UHF R3.5
R-Split
AS+
UHF R4
S-Split
Not
Used
Not
Used
7/800
Gen
AS+
UHF R3.5
R-Split


Some notes on the columns:

Now let's look at the rows. Each table is comprised of 5 rows which represent starting bandsplit edges, and 2 rows which represent ending bandsplit edges. Below are tables showing bandsplit edge values rounded to MHz (with annotations for values that are not represented in the table as integer MHz), for the CPS packages for each platform.

Table 4: Astro Bandsplit Edge Table

  Astro Mobile
Start
Edge
806 896 000 136 403 450 830 136 146 136 136 403 438 450 453 482 000 000

806 896 000 136 403 445 830 133 142 136 136 403 438 440 453 475 000 000

851 935 000 136 403 450 825 136 146 136 136 403 438 450 450 482 000 000

851 935 000 136 403 450 830 136 146 136 136 403 438 450 453 482 000 000

851 935 000 136 403 445 830 133 142 136 136 403 438 440 453 475 000 000
End
Edge
869 940 000 178 470 520 915 162 174 174 174 433 470 482 490 512 000 000

869 940 000 179 477 521 915 171 175 174 174 441 470 491 490 515 000 000
Col # 001 002 003 004 005 006 007 008 009 010 011 012 013 014 015 016 017 018
  Astro Portable
Start
Edge
806 896 000 136 403 450 830 136 146 136 136 403 438 450 453 482 000 000

806 896 000 136 403 445 830 133 142 136 136 403 438 440 453 475 000 000

851 935 000 136 403 450 825 136 146 136 136 403 438 450 450 482 000 000

851 935 000 136 403 450 830 136 146 136 136 403 438 450 453 482 000 000

851 935 000 136 403 445 830 133 142 136 136 403 438 440 453 475 000 000
End
Edge
869 940 000 178 470 520 915 162 174 174 174 433 470 482 490 512 000 000

869 940 000 179 477 521 915 171 175 174 174 441 470 491 490 515 000 000



Table 5: Astro25 Bandsplit Edge Table

  Astro25 Mobile
Start
Edge
806 896 000 136 380 450 830 136 146 136 136 403 438 450 453 481 000 000 764 450

806 896 000 136 380 450 830 136 146 136 136 403 438 450 453 481 000 000 764 450

851 935 000 136 403 450 825 136 146 136 136 403 438 450 450 482 000 000 764 450

851 935 000 136 380 450 830 136 146 136 136 403 438 450 453 482 000 000 851 450

851 935 000 136 380 450 830 136 146 136 136 403 438 450 453 482 000 000 851 450
End
Edge
869 940 000 174 470 520 915 162 174 174 174 433 470 482 490 512 000 000 869 488

869 940 000 174 470 520 915 162 174 174 174 433 470 482 490 512 000 000 869 488
Col # 001 002 003 004 005 006 007 008 009 010 011 012 013 014 015 016 017 018 019 020
  Astro25 Portable
Start
Edge
806 896 000 136 380 450 830 136 146 136 136 403 438 450 453 482 000 000 764 450

806 896 000 136 380 450 830 136 146 136 136 403 438 450 453 482 000 000 764 450

851 935 000 136 403 450 825 136 146 136 136 403 438 450 450 482 000 000 764 450

851 935 000 136 380 450 830 136 146 136 136 403 438 450 453 482 000 000 851 450

851 935 000 136 380 450 830 136 146 136 136 403 438 450 453 482 000 000 851 450
End
Edge
869 940 000 174 470 520 915 162 174 174 174 433 470 482 490 512 000 000 869 488

869 940 000 174 470 520 915 162 174 174 174 433 470 482 490 512 000 000 869 488


Now that we've seen how the tables are layed out, let's look at how to find them in the file.

Looking at Tables 4 & 5 from above, note that some rows share the same starting values. If we convert the first three frequency entry values in Hz into a little-endian longint (which is how the values are stored in the executable, this is discussed in more detail in Section 3 of this document), we get the following:

Table 6: Bandsplit Edge Table Row Finder

 Decimal Values: Frequencies in HzHex Values: Frequencies in Little-Endian LongInt
Start Rows 1-2806012500 896012500 00000000054C60A30 D4106835 00000000
Start Rows 3-5851012500 935012500 000000000946BB932 9428BB37 00000000
End Rows869987500 940987500 000000000ACF4DA33 6C541638 00000000


You should be able to use the resulting hexadecimal strings to search the executable file with your favorite hex editor (also discussed in further detail in Section 3) to find the offsets within the file. For reference, below is a list of the offsets for the current CPS as of this date:

Table 7: Bandsplit Edge Table Row in-file offsets by Platform & Version

  Astro Mobile
R05.03.00
Astro Portable
R05.03.00
Astro25 Portable
R09.01.02
Astro25 Mobile
R17.00.00
Astro25 Portable
R17.00.00
Start Row 1 0xCCA8B8 0xCA5B88 0x10462F8 0x13541C8 0x119FCD8
Start Row 2 0xCCA900 0xCA5BD0 0x1046348 0x1354218 0x119FD28
Start Row 3 0xCCA948 0xCA5C18 0x1046398 0x1354268 0x119FD78
Start Row 4 0xCCAA20 0xCA5CF0 0x1046488 0x1354358 0x119FE68
Start Row 5 0xCCAA68 0xCA5D38 0x10464D8 0x13543A8 0x119FEB8
End Row 1 0xCCAAB0 0xCA5D80 0x1046528 0x13543F8 0x119FF08
End Row 2 0xCCAAF8 0xCA5DC8 0x1046578 0x1354448 0x119FF58


If you find one of these hexadecimal strings in a part of the file far away from all the others, examine it carefully to make sure that it is in fact part of a bandsplit edge table, and that it doesn't appear in any part of the file identified as executable code by your debugger.

Please Note: There may be additional bandsplit edge values within the data-only sections of the executable, either individually or as small tables. If modifying the main bandsplit edge tables does not let you enter the desired frequency, you will probably need to search further for the necessary value to modify.


Section 2b: Bandsplit Edge Values in PE executable sections

As mentioned above, sometimes the bandsplit edge value you are looking for to allow a particular OOB frequency will not appear in data-only sections of the file. First let's look at one of the main reasons for this, the "700MHz Problem".

The 700MHz Problem

The extensive machinations surrounding the allocation of 700MHz frequencies vacated by TV broadcasters at the advent of digital TV broadcasts is outside of the scope of this document. Briefly, although the Astro25 700MHz capable radios are physically capable of and type accepted for continuous operation from 764MHz to 870MHz, the FCC rules governing use of the 700MHz spectrum allow LMR service on only portions of the spectrum from 764MHz to 806MHz. Because of this, CPS should only allow the programmer to input frequencies within these specified ranges. Additionally, between 2005 and 2008, the FCC realigned the public safety portion of 700MHz band from two 3MHz narrowband ranges (and a planned 6MHz wideband range), to two 5MHz narrowband ranges. Below is a visual synopsis of this change.

Figure 1: 700MHz Band Plan, 2005 vs 2008



Note the difference in subscriber frequency ranges. More importantly, note that the CPS still covers the pre-2008 ranges, and has been expanded to cover the post-2008 ranges only where they were not already covered. Below are the changes summarized numerically:

Table 8: 700MHz Bandsplit Edge Value changes, 2005 vs 2008

2005 ValueChanged?2008 Value
766.993750No766.993750
773.006250Yes769.006250
775.993750No775.993750
794.006250No794.006250
796.993750No796.993750
803.006250Yes799.006250


Please Note: These values do not include the radio physical bandsplit edge values as those are defined by the hardware, not software.

Under normal circumstances you would not need to modify CPS to allow these additional frequencies to be used - you would have long ago upgraded your CPS accommodate the change. However, there are circumstances in which you might be constrained to an older CPS version, say R09.01.02, which was built prior to this change. In that case, you can make these kinds of modifications.

Finding Bandsplit Edge Values in Executable Code

Values like the above 700MHz "sub" bandsplit edge values are pretty clearly not in the main bandsplit edge tables, and might reside in the executable sections of the CPS executable file. In fact, for 700MHz, this has been found to be true. Finding these values within executable code is more difficult than searching the data-only sections of the file if you are just using a hex editor, because it is hard to be sure if what you are seeing is code or data.

It's time to turn back to our handy debugger and x86 instruction set. Once you have identified the exact value to change, you can search through the analyzed code for the hex string representing the little-endian longint. What you're looking for is an instruction containing an opcode and the longint. Most commonly this is liable to be a PUSH (storing the value) or a CMP (compare). You might find something like this:

Table 9: Debugger analysis

Address Raw Code Command Mnemonic What it's doing
0x004F9EA5 68 5665B72D PUSH 2DB76556 Storing the value in a stack
0x007421DB 817D E8 5665B72D CMP DWORD PTR SS:[EBP-18],2DB76556 Comparing the value of memory at an address in a register


In this case we have searched for the frequency 766.993750 and found both a PUSH and a CMP. Note that the mnemonic will reverse the byte order of the longint.

Once you have verified that the hex string you found is indeed a data value, you can go ahead and modify it.


Section 3: Modifiying a Band Edge

The original document described the proceedure using the popular HexWorkshop hex editor. Another option is a freely available hex editor called XVI32. The proceedure is essentially the same in either application.

In the following example we will modify the CPS so that we can program 440 amateur radio frequencies into a S split (450-512) radio. The proceedure for any other band edge is the same.

Convert Values

As mentioned briefly above, the frequency values are stored in the executable file as little-endian longint (long integers), and are referenced in integer Hz.

For example:

Frequency: 450 MHz
Frequency in Hz: 450000000
Frequency in longint: 80 74 D2 1A

So, let's go convert us some numbers.

Open up XVI32, and open up the CPS exe file. (You made a backup... right?). Go to "Tools > Encode Number...". Set the encoding options, type the original frequency (in this case, 450MHz) as Hz into the input box, and press enter.

Figure 2: Encoding Frequency by Hz to LongInt (Little-Endian)



In Figure 1, we see that we have configured the encoder for LongInt, and chosen to display the output in the output box. Copy the hex string, we'll need that later.

Table 10: Converted Hex String for 450 MHz

Original ValueConverted Value (Hex String)
45000000080 74 D2 1A


We're almost ready. Use the encoder to encode the longint for 440 MHz, and copy the hex string:

Table 11: Converted Hex String for 440 MHz

Original ValueConverted Value (Hex String)
44000000000 DE 39 1A


Replace Values

Locate each instance of the original value you wish to change. Once you've located the string, go to "Edit > Overwrite String...". Paste in the 440 MHz hex string, and click on Overwrite. You've now replaced that instance of 450 MHz with 440 MHz.

Once you've replaced all the original values, save the modified file, and open CPS. You should now be able to program frequencies as low as 440.000 MHz into the CPS without it complaining.

Happy hacking!
Copyright © 2000-2014 by Peter "Akardam" Acord questions, comments, suggestions? contact me