[chirp_devel] Baofeng UV-6 Radio
I've have been loaned a Baofeng UV-6 radio. I think it should get its own uv6.py file. What is the correct procedure to get it started.
Thanks, Jim KC9HI
On Jan 30, 2014 5:36 PM, "Jim Unroe" rock.unroe@gmail.com wrote:
I've have been loaned a Baofeng UV-6 radio. I think it should get its own
uv6.py file. What is the correct procedure to get it started.
There's not much to it.
cp uv5r.py uv6.py
Then modify uv6.py as needed to support the UV-6.
If you decide there are significant similarities and they should share some code, ask specifically about that code and we'll try to figure out the best way to combine them.
Tom KD7LXL
On Thu, Jan 30, 2014 at 10:31 PM, Tom Hayward esarfl@gmail.com wrote:
On Jan 30, 2014 5:36 PM, "Jim Unroe" rock.unroe@gmail.com wrote:
I've have been loaned a Baofeng UV-6 radio. I think it should get its
own uv6.py file. What is the correct procedure to get it started.
There's not much to it.
cp uv5r.py uv6.py
Then modify uv6.py as needed to support the UV-6.
If you decide there are significant similarities and they should share some code, ask specifically about that code and we'll try to figure out the best way to combine them.
Tom KD7LXL
Tom,
I created the uv6.py file last weekend. It is working and fairly complete.
This radio doesn't have a keypad or display. So in a lot of ways this radio is quite similar to a UV-5R and in a lot of other ways it is quite different.
The memory layout that it uses is largely the same, but a few bytes here and there are used for different purpose in this radio than the others.
I've ripped out 99% of the structure and code from the uv5r.py that isn't used or necessary. I've also borrowed from other radios as well as cleaned up the code from what I've learn by 'hacking' on the uv5r.py file for the last 13 months.
My plans were to submit the uv6.py file without the settings menus. Then follow that up with the Basic Settings after going over them one last time. And then the same of the additional menus. But I can try to combine this up if it is the right thing to do.
Jim KC9HI
Jim
I created the uv6.py file last weekend. It is working and fairly complete.
Nice!
This radio doesn't have a keypad or display. So in a lot of ways this radio is quite similar to a UV-5R and in a lot of other ways it is quite different.
The memory layout that it uses is largely the same, but a few bytes here and there are used for different purpose in this radio than the others.
Can you give a few details of the differences? If it's, say, five bytes in memory that do different things then it might be best to keep the drivers unified and call out the differences. If it's fifty, then separate seems better. I'm sure you're making the right call here by having them separate, but we should just circle around and make sure that's what we want to do. It would be unfortunate to have to maintain two pieces of mostly-identical code going forward.
I've ripped out 99% of the structure and code from the uv5r.py that isn't used or necessary. I've also borrowed from other radios as well as cleaned up the code from what I've learn by 'hacking' on the uv5r.py file for the last 13 months.
Ripped out 99% of the non-overlapping code or 99% of the UV5 code entirely?
My plans were to submit the uv6.py file without the settings menus. Then follow that up with the Basic Settings after going over them one last time. And then the same of the additional menus. But I can try to combine this up if it is the right thing to do.
If they're going to be separate, then doing it incrementally, starting with minimal function is definitely fine with me.
--Dan
On Fri, Jan 31, 2014 at 9:43 AM, Dan Smith dsmith@danplanet.com wrote:
I've ripped out 99% of the structure and code from the uv5r.py that isn't used or necessary. I've also borrowed from other radios as well as cleaned up the code from what I've learn by 'hacking' on the uv5r.py file for the last 13 months.
Ripped out 99% of the non-overlapping code or 99% of the UV5 code entirely?
What I meant was that if there were 100 lines of code that was not used for the UV-6, I have only removed 99 lines of it. I haven't removed the code for adjusting the band limits or the power-on messages yet. Sorry for the confusion.
I was trying to look over every settings to see if it could be utilized by the radio. I didn't want to remove it just because the OEM software didn't have it. If is still did something that the could be utilized by the user/radio, I wanted to leave it in.
If the UV-6 was going to be supported by a separate uv6.py driver, which was my goal, then I wanted to be sure it was completely sanitized from any unnecessary UV-5R, F-11, UV-82 and some left over BJ-UV-55 code in the structure or anywhere else.
What I was trying to avoid was to add it in and then find out it needed to be separate like the UV-55.
Jim
On Fri, Jan 31, 2014 at 9:43 AM, Dan Smith dsmith@danplanet.com wrote:
Can you give a few details of the differences? If it's, say, five bytes in memory that do different things then it might be best to keep the drivers unified and call out the differences. If it's fifty, then separate seems better. I'm sure you're making the right call here by having them separate, but we should just circle around and make sure that's what we want to do. It would be unfortunate to have to maintain two pieces of mostly-identical code going forward.
There is only 1 conflict in the 'settings' structure.
u8 autolk; # UV-5R/UV-82/F-11
u8 voxenable; # UV-6
And then the one other byte is identified where is wasn't before.
The rest would be just be making sure the settings were the right ones for each radio type.
Jim
On Fri, Jan 31, 2014 at 6:41 PM, Jim Unroe rock.unroe@gmail.com wrote:
On Fri, Jan 31, 2014 at 9:43 AM, Dan Smith dsmith@danplanet.com wrote:
Can you give a few details of the differences? If it's, say, five bytes in memory that do different things then it might be best to keep the drivers unified and call out the differences. If it's fifty, then separate seems better. I'm sure you're making the right call here by having them separate, but we should just circle around and make sure that's what we want to do. It would be unfortunate to have to maintain two pieces of mostly-identical code going forward.
There is only 1 conflict in the 'settings' structure.
u8 autolk; # UV-5R/UV-82/F-11
u8 voxenable; # UV-6
And then the one other byte is identified where is wasn't before.
The rest would be just be making sure the settings were the right ones for each radio type.
Jim
I need to start thinking about sending this radio back to it's owner.
I've attached what I've done in the hope that it would help with giving me direction.
Thanks, Jim
I've attached what I've done in the hope that it would help with giving me direction.
I just diffed that with the UV5 driver and it looks really close. I think it would be best to unify them if at all possible. If I get you started on a subclass that can override things for the UV6 where they differ from the UV5, would you be okay taking a stab at finishing them?
--Dan
On Tue, Feb 4, 2014 at 1:34 PM, Dan Smith dsmith@danplanet.com wrote:
I've attached what I've done in the hope that it would help with giving me direction.
I just diffed that with the UV5 driver and it looks really close. I think it would be best to unify them if at all possible. If I get you started on a subclass that can override things for the UV6 where they differ from the UV5, would you be okay taking a stab at finishing them?
--Dan
Yes. I'm sure that with a little guidance, I can handle it. I believe Jens was doing some of that when he was originally adding the BJ UV-55 to uv5r.py.
Jim
Yeah, take a look with what I did with bjuv55.py I did that because there was a significant enough difference to put the subclass in a new module, but enough similarities to inherit from uv5r and not just copy it.
i think the way that bitwise memory map definitions are setup today (basically structures) make it difficult to do Object oriented stuff to it like inheritance and overriding just parts.
It seems that if there are any differences in your custom model's memmap, some choices are:
1. make a separate complete copy of the memory map for that model and modify slightly (like I did in bjuv55.py). This is good for a large amount of differences. But as this is lots of code real estate its best suited for subclassing in another module
2. if there are just differences in the offsets of certain parts of the memory map, but otherwise are the same, use a print format hack to set the offset when MEM_FORMAT is bitwise.parse'd. You can see this in action with the poweron_msg struct of the memmap that I did (based upon the idea from some other radio classes doing similar.)
3. statically create slightly differently named sections of the memory map unique to each radio, and then elsewhere detect and dynamically change the memory object property name to match the setting you are looking at. Looks like you might have already done this from looking at things like "sixpoweron_msg" vs "poweron_msg".
I think as we see more and more of UV-5R clones with ever-so-slight differences it will become more critical to streamline this class.
Dan, this reminds me - is there a way to "incrementally" load the bitwise structures into the memory map. The thought here was we could have a "common" channel map, and then might have custom settings, or event sections of settings depending upon model, and load the ones needed into the radio class. (This could be thought of as a piecemeal approach to populating the memory map?)
________________________________ From: Jim Unroe rock.unroe@gmail.com To: chirp-devel chirp_devel@intrepid.danplanet.com Sent: Tuesday, February 4, 2014 1:23 PM Subject: Re: [chirp_devel] Baofeng UV-6 Radio
On Tue, Feb 4, 2014 at 1:34 PM, Dan Smith dsmith@danplanet.com wrote:
I've attached what I've done in the hope that it would help with giving
me direction.
I just diffed that with the UV5 driver and it looks really close. I think it would be best to unify them if at all possible. If I get you started on a subclass that can override things for the UV6 where they differ from the UV5, would you be okay taking a stab at finishing them?
--Dan
Yes. I'm sure that with a little guidance, I can handle it. I believe Jens was doing some of that when he was originally adding the BJ UV-55 to uv5r.py.
Jim
_______________________________________________ chirp_devel mailing list chirp_devel@intrepid.danplanet.com http://intrepid.danplanet.com/mailman/listinfo/chirp_devel Developer docs: http://chirp.danplanet.com/projects/chirp/wiki/Developers
Dan, this reminds me - is there a way to "incrementally" load the bitwise structures into the memory map. The thought here was we could have a "common" channel map, and then might have custom settings, or event sections of settings depending upon model, and load the ones needed into the radio class. (This could be thought of as a piecemeal approach to populating the memory map?)
They're just strings, so you can format them, concatenate pieces together, than then pass the result to bitwise to do the magic. There is at least one other case where I format in the address of a starting block depending on which model I'm using. I think that is actually no longer necessary in that case, now that structs can be defined as types and applied in multiple places (a relatively recent bitwise feature). However, for your case where you want to piece things together, I think it should be pretty easy to do, right?
--Dan
Yeah thats where I was going with in regards to the way uv5r is setup. In order to make it more generalized, and handle lots of slightly different edge cases, we could split the memory map up into a few sections.
I'll have to look at it some more, and also what you are talking about type-wise…
________________________________ From: Dan Smith dsmith@danplanet.com To: chirp_devel@intrepid.danplanet.com Sent: Wednesday, February 5, 2014 7:45 PM Subject: Re: [chirp_devel] Baofeng UV-6 Radio
Dan, this reminds me - is there a way to "incrementally" load the bitwise structures into the memory map. The thought here was we could have a "common" channel map, and then might have custom settings, or event sections of settings depending upon model, and load the ones needed into the radio class. (This could be thought of as a piecemeal approach to populating the memory map?)
They're just strings, so you can format them, concatenate pieces together, than then pass the result to bitwise to do the magic. There is at least one other case where I format in the address of a starting block depending on which model I'm using. I think that is actually no longer necessary in that case, now that structs can be defined as types and applied in multiple places (a relatively recent bitwise feature). However, for your case where you want to piece things together, I think it should be pretty easy to do, right?
--Dan
_______________________________________________ chirp_devel mailing list chirp_devel@intrepid.danplanet.com http://intrepid.danplanet.com/mailman/listinfo/chirp_devel Developer docs: http://chirp.danplanet.com/projects/chirp/wiki/Developers
Yes. I'm sure that with a little guidance, I can handle it. I believe Jens was doing some of that when he was originally adding the BJ UV-55 to uv5r.py.
Okay, here is something to get you started. Sorry this took so long. This is far from complete, but I hope it will help get you going.
First, I've attached a diff of everything that you changed on the UV5 driver to arrive at the UV6 driver. That gives you a concise mapping of things that need to be done.
Second, I've attached a patch against the UV5 driver which adds a subclass of the base UV5 driver for the UV6. You can override things in this subclass -- anything you don't override is used from the base class as-is. You can see that I added an override for the _is_orig() method to always return False in the case of the UV6. Also, I overrode the _get_settings() method entirely. I figure that a good first start will be to just put the settings stuff that you have figured out for the UV6 into that method, even if it duplicates some of what is already there for the UV5. Later, we can reconcile those, but it will be simpler to do it that way I think.
I applied some (but probably not all) of your changes to the cloning functions near the top so that they will do the right thing for the UV6. I think that since we can always check radio.MODEL and do something specific for the UV6, we should be able to handle all the cases.
For the memory format changes, you can just leave any of the structures that apply only to the uv5 -- they won't hurt the uv6 in that case. It looks like the only conflict is that the uv5 calls one byte "autolk" and the uv6 calls it "voxenable". If it were me, I would just leave it as autolk and put a comment in the UV6 settings code like:
# NOTE: The UV6 calls this byte voxenable, but the UV5 calls it # autolk. Since this is a minor difference, we'll refer to it by the # wrong name here.
We can apply some sneakier techniques later to make it look right, but the comment should be enough for now since it's really the only discrepancy in the settings block.
It also looks like the two radios count their memories differently, one being from zero and the other from one. In that case, you might just add a method like this for the uv5:
def _get_mem(self, number): return self._memobj.memory[number]
and then override it in the UV6 class like this:
def _get_mem(self, number): return self._memobj.memory[number - 1]
then in get_memory(), you can do this:
mem = self._get_mem(number)
and it will do the right thing in each class.
Make sense? I know it's a little more complicated to do it this way, but I think it will end up with a *lot* less maintenance in the long-run.
Thanks a lot for doing this, and of course, ask if you have questions!
--Dan
On Wed, Feb 5, 2014 at 8:17 PM, Dan Smith dsmith@danplanet.com wrote:
Yes. I'm sure that with a little guidance, I can handle it. I believe Jens was doing some of that when he was originally adding the BJ UV-55 to uv5r.py.
Okay, here is something to get you started. Sorry this took so long. This is far from complete, but I hope it will help get you going.
Thanks Dan. The snow didn't keep me from going to work today so this was
perfect timing. I was studying some other drivers this evening for ideas. Hopefully I can devote some time during the upcoming weekend to work on this.
Jim
Make sense? I know it's a little more complicated to do it this way, but I think it will end up with a *lot* less maintenance in the long-run.
Thanks a lot for doing this, and of course, ask if you have questions!
All is going well. I've learned some nice things as a result.
I have a question though. Since the use picks a model from a list, shouldn't there be a way to take advantage of that for enabling and/or disabling settings? I've been using self._my_version() to do this but if I'm not careful, there can be collisions with the various models. It seem to me that the user selected model would be much better.
Jim
I have a question though. Since the use picks a model from a list, shouldn't there be a way to take advantage of that for enabling and/or disabling settings? I've been using self._my_version() to do this but if I'm not careful, there can be collisions with the various models. It seem to me that the user selected model would be much better.
Well, yes, but for that to work reliably, you need to be able to detect the image separately as well. If that's working, then you can do something like:
if self.MODEL == "UV-5R": # do something elif self.MODEL == "UV6": # do something different
--Dan
On Sun, Feb 16, 2014 at 2:01 PM, Dan Smith dsmith@danplanet.com wrote:
I have a question though. Since the use picks a model from a list, shouldn't there be a way to take advantage of that for enabling and/or disabling settings? I've been using self._my_version() to do this but if I'm not careful, there can be collisions with the various models. It seem to me that the user selected model would be much better.
Well, yes, but for that to work reliably, you need to be able to detect the image separately as well.
I'm not sure I completely follow this. After I load an image, CHIRP does properly select UV-5R, F-11, UV-82 or UV-6 when an "Upload To Radio" is attempted. Is that what you mean, or something else.
Jim
On Wed, Feb 5, 2014 at 8:17 PM, Dan Smith dsmith@danplanet.com wrote:
It also looks like the two radios count their memories differently, one being from zero and the other from one. In that case, you might just add a method like this for the uv5:
def _get_mem(self, number): return self._memobj.memory[number]
and then override it in the UV6 class like this:
def _get_mem(self, number): return self._memobj.memory[number - 1]
then in get_memory(), you can do this:
mem = self._get_mem(number)
and it will do the right thing in each class.
Apparently I need to do something similar for set_memory(). I've tried to do it similar to the above but can't quite get it. Here are the original lines...
def set_memory(self, mem): _mem = self._memobj.memory[mem.number]
Thanks, Jim
On Sun, Feb 16, 2014 at 7:00 PM, Jim Unroe rock.unroe@gmail.com wrote:
On Wed, Feb 5, 2014 at 8:17 PM, Dan Smith dsmith@danplanet.com wrote:
It also looks like the two radios count their memories differently, one being from zero and the other from one. In that case, you might just add a method like this for the uv5:
def _get_mem(self, number): return self._memobj.memory[number]
and then override it in the UV6 class like this:
def _get_mem(self, number): return self._memobj.memory[number - 1]
then in get_memory(), you can do this:
mem = self._get_mem(number)
and it will do the right thing in each class.
Apparently I need to do something similar for set_memory(). I've tried to do it similar to the above but can't quite get it. Here are the original lines...
def set_memory(self, mem): _mem = self._memobj.memory[mem.number]
I think I may have figure it out on my own.
def _set_mem(self, number): return self._memobj.memory[number]
def set_memory(self, mem): _mem = self._get_mem(mem.number)
Jim
Dan and Jens,
Attached is the current state of where I am. I've tested this with the various .img files that I have for the UV-5R, UV-82, F-11, UV-6 and the BJ UV-55 that Jens supplied. They all appear to work as expected.
Unfortunately the only radio I currently have to testing downloads and uploads is my UV-5R. I returned the radio to Jack. He has been testing the UV-6 for me. Last evening I corrected the issue that he reported but I am still waiting to hear from him for confirmation.
I know I still have some commented code to remove. I'm still testing to make sure that using "if self.MODEL ==" will work for hiding/showing menu selections. So far it appears to work as expected.
Jens. Please test this with your UV-55 to make sure I didn't break anything for you.
I'm looking forward to your comments. Thanks guys.
Jim
participants (4)
-
Dan Smith
-
Jens J.
-
Jim Unroe
-
Tom Hayward