├── License.txt ├── Makefile ├── README.md ├── boot.h ├── optiboot.c ├── pin_defs.h └── stk500.h /License.txt: -------------------------------------------------------------------------------- 1 | GNU GENERAL PUBLIC LICENSE 2 | Version 3, 29 June 2007 3 | 4 | Copyright (C) 2007 Free Software Foundation, Inc. 5 | Everyone is permitted to copy and distribute verbatim copies 6 | of this license document, but changing it is not allowed. 7 | 8 | Preamble 9 | 10 | The GNU General Public License is a free, copyleft license for 11 | software and other kinds of works. 12 | 13 | The licenses for most software and other practical works are designed 14 | to take away your freedom to share and change the works. By contrast, 15 | the GNU General Public License is intended to guarantee your freedom to 16 | share and change all versions of a program--to make sure it remains free 17 | software for all its users. We, the Free Software Foundation, use the 18 | GNU General Public License for most of our software; it applies also to 19 | any other work released this way by its authors. You can apply it to 20 | your programs, too. 21 | 22 | When we speak of free software, we are referring to freedom, not 23 | price. Our General Public Licenses are designed to make sure that you 24 | have the freedom to distribute copies of free software (and charge for 25 | them if you wish), that you receive source code or can get it if you 26 | want it, that you can change the software or use pieces of it in new 27 | free programs, and that you know you can do these things. 28 | 29 | To protect your rights, we need to prevent others from denying you 30 | these rights or asking you to surrender the rights. Therefore, you have 31 | certain responsibilities if you distribute copies of the software, or if 32 | you modify it: responsibilities to respect the freedom of others. 33 | 34 | For example, if you distribute copies of such a program, whether 35 | gratis or for a fee, you must pass on to the recipients the same 36 | freedoms that you received. You must make sure that they, too, receive 37 | or can get the source code. And you must show them these terms so they 38 | know their rights. 39 | 40 | Developers that use the GNU GPL protect your rights with two steps: 41 | (1) assert copyright on the software, and (2) offer you this License 42 | giving you legal permission to copy, distribute and/or modify it. 43 | 44 | For the developers' and authors' protection, the GPL clearly explains 45 | that there is no warranty for this free software. For both users' and 46 | authors' sake, the GPL requires that modified versions be marked as 47 | changed, so that their problems will not be attributed erroneously to 48 | authors of previous versions. 49 | 50 | Some devices are designed to deny users access to install or run 51 | modified versions of the software inside them, although the manufacturer 52 | can do so. This is fundamentally incompatible with the aim of 53 | protecting users' freedom to change the software. The systematic 54 | pattern of such abuse occurs in the area of products for individuals to 55 | use, which is precisely where it is most unacceptable. Therefore, we 56 | have designed this version of the GPL to prohibit the practice for those 57 | products. If such problems arise substantially in other domains, we 58 | stand ready to extend this provision to those domains in future versions 59 | of the GPL, as needed to protect the freedom of users. 60 | 61 | Finally, every program is threatened constantly by software patents. 62 | States should not allow patents to restrict development and use of 63 | software on general-purpose computers, but in those that do, we wish to 64 | avoid the special danger that patents applied to a free program could 65 | make it effectively proprietary. To prevent this, the GPL assures that 66 | patents cannot be used to render the program non-free. 67 | 68 | The precise terms and conditions for copying, distribution and 69 | modification follow. 70 | 71 | TERMS AND CONDITIONS 72 | 73 | 0. Definitions. 74 | 75 | "This License" refers to version 3 of the GNU General Public License. 76 | 77 | "Copyright" also means copyright-like laws that apply to other kinds of 78 | works, such as semiconductor masks. 79 | 80 | "The Program" refers to any copyrightable work licensed under this 81 | License. Each licensee is addressed as "you". "Licensees" and 82 | "recipients" may be individuals or organizations. 83 | 84 | To "modify" a work means to copy from or adapt all or part of the work 85 | in a fashion requiring copyright permission, other than the making of an 86 | exact copy. The resulting work is called a "modified version" of the 87 | earlier work or a work "based on" the earlier work. 88 | 89 | A "covered work" means either the unmodified Program or a work based 90 | on the Program. 91 | 92 | To "propagate" a work means to do anything with it that, without 93 | permission, would make you directly or secondarily liable for 94 | infringement under applicable copyright law, except executing it on a 95 | computer or modifying a private copy. Propagation includes copying, 96 | distribution (with or without modification), making available to the 97 | public, and in some countries other activities as well. 98 | 99 | To "convey" a work means any kind of propagation that enables other 100 | parties to make or receive copies. Mere interaction with a user through 101 | a computer network, with no transfer of a copy, is not conveying. 102 | 103 | An interactive user interface displays "Appropriate Legal Notices" 104 | to the extent that it includes a convenient and prominently visible 105 | feature that (1) displays an appropriate copyright notice, and (2) 106 | tells the user that there is no warranty for the work (except to the 107 | extent that warranties are provided), that licensees may convey the 108 | work under this License, and how to view a copy of this License. If 109 | the interface presents a list of user commands or options, such as a 110 | menu, a prominent item in the list meets this criterion. 111 | 112 | 1. Source Code. 113 | 114 | The "source code" for a work means the preferred form of the work 115 | for making modifications to it. "Object code" means any non-source 116 | form of a work. 117 | 118 | A "Standard Interface" means an interface that either is an official 119 | standard defined by a recognized standards body, or, in the case of 120 | interfaces specified for a particular programming language, one that 121 | is widely used among developers working in that language. 122 | 123 | The "System Libraries" of an executable work include anything, other 124 | than the work as a whole, that (a) is included in the normal form of 125 | packaging a Major Component, but which is not part of that Major 126 | Component, and (b) serves only to enable use of the work with that 127 | Major Component, or to implement a Standard Interface for which an 128 | implementation is available to the public in source code form. A 129 | "Major Component", in this context, means a major essential component 130 | (kernel, window system, and so on) of the specific operating system 131 | (if any) on which the executable work runs, or a compiler used to 132 | produce the work, or an object code interpreter used to run it. 133 | 134 | The "Corresponding Source" for a work in object code form means all 135 | the source code needed to generate, install, and (for an executable 136 | work) run the object code and to modify the work, including scripts to 137 | control those activities. However, it does not include the work's 138 | System Libraries, or general-purpose tools or generally available free 139 | programs which are used unmodified in performing those activities but 140 | which are not part of the work. For example, Corresponding Source 141 | includes interface definition files associated with source files for 142 | the work, and the source code for shared libraries and dynamically 143 | linked subprograms that the work is specifically designed to require, 144 | such as by intimate data communication or control flow between those 145 | subprograms and other parts of the work. 146 | 147 | The Corresponding Source need not include anything that users 148 | can regenerate automatically from other parts of the Corresponding 149 | Source. 150 | 151 | The Corresponding Source for a work in source code form is that 152 | same work. 153 | 154 | 2. Basic Permissions. 155 | 156 | All rights granted under this License are granted for the term of 157 | copyright on the Program, and are irrevocable provided the stated 158 | conditions are met. This License explicitly affirms your unlimited 159 | permission to run the unmodified Program. The output from running a 160 | covered work is covered by this License only if the output, given its 161 | content, constitutes a covered work. This License acknowledges your 162 | rights of fair use or other equivalent, as provided by copyright law. 163 | 164 | You may make, run and propagate covered works that you do not 165 | convey, without conditions so long as your license otherwise remains 166 | in force. You may convey covered works to others for the sole purpose 167 | of having them make modifications exclusively for you, or provide you 168 | with facilities for running those works, provided that you comply with 169 | the terms of this License in conveying all material for which you do 170 | not control copyright. Those thus making or running the covered works 171 | for you must do so exclusively on your behalf, under your direction 172 | and control, on terms that prohibit them from making any copies of 173 | your copyrighted material outside their relationship with you. 174 | 175 | Conveying under any other circumstances is permitted solely under 176 | the conditions stated below. Sublicensing is not allowed; section 10 177 | makes it unnecessary. 178 | 179 | 3. Protecting Users' Legal Rights From Anti-Circumvention Law. 180 | 181 | No covered work shall be deemed part of an effective technological 182 | measure under any applicable law fulfilling obligations under article 183 | 11 of the WIPO copyright treaty adopted on 20 December 1996, or 184 | similar laws prohibiting or restricting circumvention of such 185 | measures. 186 | 187 | When you convey a covered work, you waive any legal power to forbid 188 | circumvention of technological measures to the extent such circumvention 189 | is effected by exercising rights under this License with respect to 190 | the covered work, and you disclaim any intention to limit operation or 191 | modification of the work as a means of enforcing, against the work's 192 | users, your or third parties' legal rights to forbid circumvention of 193 | technological measures. 194 | 195 | 4. Conveying Verbatim Copies. 196 | 197 | You may convey verbatim copies of the Program's source code as you 198 | receive it, in any medium, provided that you conspicuously and 199 | appropriately publish on each copy an appropriate copyright notice; 200 | keep intact all notices stating that this License and any 201 | non-permissive terms added in accord with section 7 apply to the code; 202 | keep intact all notices of the absence of any warranty; and give all 203 | recipients a copy of this License along with the Program. 204 | 205 | You may charge any price or no price for each copy that you convey, 206 | and you may offer support or warranty protection for a fee. 207 | 208 | 5. Conveying Modified Source Versions. 209 | 210 | You may convey a work based on the Program, or the modifications to 211 | produce it from the Program, in the form of source code under the 212 | terms of section 4, provided that you also meet all of these conditions: 213 | 214 | a) The work must carry prominent notices stating that you modified 215 | it, and giving a relevant date. 216 | 217 | b) The work must carry prominent notices stating that it is 218 | released under this License and any conditions added under section 219 | 7. This requirement modifies the requirement in section 4 to 220 | "keep intact all notices". 221 | 222 | c) You must license the entire work, as a whole, under this 223 | License to anyone who comes into possession of a copy. This 224 | License will therefore apply, along with any applicable section 7 225 | additional terms, to the whole of the work, and all its parts, 226 | regardless of how they are packaged. This License gives no 227 | permission to license the work in any other way, but it does not 228 | invalidate such permission if you have separately received it. 229 | 230 | d) If the work has interactive user interfaces, each must display 231 | Appropriate Legal Notices; however, if the Program has interactive 232 | interfaces that do not display Appropriate Legal Notices, your 233 | work need not make them do so. 234 | 235 | A compilation of a covered work with other separate and independent 236 | works, which are not by their nature extensions of the covered work, 237 | and which are not combined with it such as to form a larger program, 238 | in or on a volume of a storage or distribution medium, is called an 239 | "aggregate" if the compilation and its resulting copyright are not 240 | used to limit the access or legal rights of the compilation's users 241 | beyond what the individual works permit. Inclusion of a covered work 242 | in an aggregate does not cause this License to apply to the other 243 | parts of the aggregate. 244 | 245 | 6. Conveying Non-Source Forms. 246 | 247 | You may convey a covered work in object code form under the terms 248 | of sections 4 and 5, provided that you also convey the 249 | machine-readable Corresponding Source under the terms of this License, 250 | in one of these ways: 251 | 252 | a) Convey the object code in, or embodied in, a physical product 253 | (including a physical distribution medium), accompanied by the 254 | Corresponding Source fixed on a durable physical medium 255 | customarily used for software interchange. 256 | 257 | b) Convey the object code in, or embodied in, a physical product 258 | (including a physical distribution medium), accompanied by a 259 | written offer, valid for at least three years and valid for as 260 | long as you offer spare parts or customer support for that product 261 | model, to give anyone who possesses the object code either (1) a 262 | copy of the Corresponding Source for all the software in the 263 | product that is covered by this License, on a durable physical 264 | medium customarily used for software interchange, for a price no 265 | more than your reasonable cost of physically performing this 266 | conveying of source, or (2) access to copy the 267 | Corresponding Source from a network server at no charge. 268 | 269 | c) Convey individual copies of the object code with a copy of the 270 | written offer to provide the Corresponding Source. This 271 | alternative is allowed only occasionally and noncommercially, and 272 | only if you received the object code with such an offer, in accord 273 | with subsection 6b. 274 | 275 | d) Convey the object code by offering access from a designated 276 | place (gratis or for a charge), and offer equivalent access to the 277 | Corresponding Source in the same way through the same place at no 278 | further charge. You need not require recipients to copy the 279 | Corresponding Source along with the object code. If the place to 280 | copy the object code is a network server, the Corresponding Source 281 | may be on a different server (operated by you or a third party) 282 | that supports equivalent copying facilities, provided you maintain 283 | clear directions next to the object code saying where to find the 284 | Corresponding Source. Regardless of what server hosts the 285 | Corresponding Source, you remain obligated to ensure that it is 286 | available for as long as needed to satisfy these requirements. 287 | 288 | e) Convey the object code using peer-to-peer transmission, provided 289 | you inform other peers where the object code and Corresponding 290 | Source of the work are being offered to the general public at no 291 | charge under subsection 6d. 292 | 293 | A separable portion of the object code, whose source code is excluded 294 | from the Corresponding Source as a System Library, need not be 295 | included in conveying the object code work. 296 | 297 | A "User Product" is either (1) a "consumer product", which means any 298 | tangible personal property which is normally used for personal, family, 299 | or household purposes, or (2) anything designed or sold for incorporation 300 | into a dwelling. In determining whether a product is a consumer product, 301 | doubtful cases shall be resolved in favor of coverage. For a particular 302 | product received by a particular user, "normally used" refers to a 303 | typical or common use of that class of product, regardless of the status 304 | of the particular user or of the way in which the particular user 305 | actually uses, or expects or is expected to use, the product. A product 306 | is a consumer product regardless of whether the product has substantial 307 | commercial, industrial or non-consumer uses, unless such uses represent 308 | the only significant mode of use of the product. 309 | 310 | "Installation Information" for a User Product means any methods, 311 | procedures, authorization keys, or other information required to install 312 | and execute modified versions of a covered work in that User Product from 313 | a modified version of its Corresponding Source. The information must 314 | suffice to ensure that the continued functioning of the modified object 315 | code is in no case prevented or interfered with solely because 316 | modification has been made. 317 | 318 | If you convey an object code work under this section in, or with, or 319 | specifically for use in, a User Product, and the conveying occurs as 320 | part of a transaction in which the right of possession and use of the 321 | User Product is transferred to the recipient in perpetuity or for a 322 | fixed term (regardless of how the transaction is characterized), the 323 | Corresponding Source conveyed under this section must be accompanied 324 | by the Installation Information. But this requirement does not apply 325 | if neither you nor any third party retains the ability to install 326 | modified object code on the User Product (for example, the work has 327 | been installed in ROM). 328 | 329 | The requirement to provide Installation Information does not include a 330 | requirement to continue to provide support service, warranty, or updates 331 | for a work that has been modified or installed by the recipient, or for 332 | the User Product in which it has been modified or installed. Access to a 333 | network may be denied when the modification itself materially and 334 | adversely affects the operation of the network or violates the rules and 335 | protocols for communication across the network. 336 | 337 | Corresponding Source conveyed, and Installation Information provided, 338 | in accord with this section must be in a format that is publicly 339 | documented (and with an implementation available to the public in 340 | source code form), and must require no special password or key for 341 | unpacking, reading or copying. 342 | 343 | 7. Additional Terms. 344 | 345 | "Additional permissions" are terms that supplement the terms of this 346 | License by making exceptions from one or more of its conditions. 347 | Additional permissions that are applicable to the entire Program shall 348 | be treated as though they were included in this License, to the extent 349 | that they are valid under applicable law. If additional permissions 350 | apply only to part of the Program, that part may be used separately 351 | under those permissions, but the entire Program remains governed by 352 | this License without regard to the additional permissions. 353 | 354 | When you convey a copy of a covered work, you may at your option 355 | remove any additional permissions from that copy, or from any part of 356 | it. (Additional permissions may be written to require their own 357 | removal in certain cases when you modify the work.) You may place 358 | additional permissions on material, added by you to a covered work, 359 | for which you have or can give appropriate copyright permission. 360 | 361 | Notwithstanding any other provision of this License, for material you 362 | add to a covered work, you may (if authorized by the copyright holders of 363 | that material) supplement the terms of this License with terms: 364 | 365 | a) Disclaiming warranty or limiting liability differently from the 366 | terms of sections 15 and 16 of this License; or 367 | 368 | b) Requiring preservation of specified reasonable legal notices or 369 | author attributions in that material or in the Appropriate Legal 370 | Notices displayed by works containing it; or 371 | 372 | c) Prohibiting misrepresentation of the origin of that material, or 373 | requiring that modified versions of such material be marked in 374 | reasonable ways as different from the original version; or 375 | 376 | d) Limiting the use for publicity purposes of names of licensors or 377 | authors of the material; or 378 | 379 | e) Declining to grant rights under trademark law for use of some 380 | trade names, trademarks, or service marks; or 381 | 382 | f) Requiring indemnification of licensors and authors of that 383 | material by anyone who conveys the material (or modified versions of 384 | it) with contractual assumptions of liability to the recipient, for 385 | any liability that these contractual assumptions directly impose on 386 | those licensors and authors. 387 | 388 | All other non-permissive additional terms are considered "further 389 | restrictions" within the meaning of section 10. If the Program as you 390 | received it, or any part of it, contains a notice stating that it is 391 | governed by this License along with a term that is a further 392 | restriction, you may remove that term. If a license document contains 393 | a further restriction but permits relicensing or conveying under this 394 | License, you may add to a covered work material governed by the terms 395 | of that license document, provided that the further restriction does 396 | not survive such relicensing or conveying. 397 | 398 | If you add terms to a covered work in accord with this section, you 399 | must place, in the relevant source files, a statement of the 400 | additional terms that apply to those files, or a notice indicating 401 | where to find the applicable terms. 402 | 403 | Additional terms, permissive or non-permissive, may be stated in the 404 | form of a separately written license, or stated as exceptions; 405 | the above requirements apply either way. 406 | 407 | 8. Termination. 408 | 409 | You may not propagate or modify a covered work except as expressly 410 | provided under this License. Any attempt otherwise to propagate or 411 | modify it is void, and will automatically terminate your rights under 412 | this License (including any patent licenses granted under the third 413 | paragraph of section 11). 414 | 415 | However, if you cease all violation of this License, then your 416 | license from a particular copyright holder is reinstated (a) 417 | provisionally, unless and until the copyright holder explicitly and 418 | finally terminates your license, and (b) permanently, if the copyright 419 | holder fails to notify you of the violation by some reasonable means 420 | prior to 60 days after the cessation. 421 | 422 | Moreover, your license from a particular copyright holder is 423 | reinstated permanently if the copyright holder notifies you of the 424 | violation by some reasonable means, this is the first time you have 425 | received notice of violation of this License (for any work) from that 426 | copyright holder, and you cure the violation prior to 30 days after 427 | your receipt of the notice. 428 | 429 | Termination of your rights under this section does not terminate the 430 | licenses of parties who have received copies or rights from you under 431 | this License. If your rights have been terminated and not permanently 432 | reinstated, you do not qualify to receive new licenses for the same 433 | material under section 10. 434 | 435 | 9. Acceptance Not Required for Having Copies. 436 | 437 | You are not required to accept this License in order to receive or 438 | run a copy of the Program. Ancillary propagation of a covered work 439 | occurring solely as a consequence of using peer-to-peer transmission 440 | to receive a copy likewise does not require acceptance. However, 441 | nothing other than this License grants you permission to propagate or 442 | modify any covered work. These actions infringe copyright if you do 443 | not accept this License. Therefore, by modifying or propagating a 444 | covered work, you indicate your acceptance of this License to do so. 445 | 446 | 10. Automatic Licensing of Downstream Recipients. 447 | 448 | Each time you convey a covered work, the recipient automatically 449 | receives a license from the original licensors, to run, modify and 450 | propagate that work, subject to this License. You are not responsible 451 | for enforcing compliance by third parties with this License. 452 | 453 | An "entity transaction" is a transaction transferring control of an 454 | organization, or substantially all assets of one, or subdividing an 455 | organization, or merging organizations. If propagation of a covered 456 | work results from an entity transaction, each party to that 457 | transaction who receives a copy of the work also receives whatever 458 | licenses to the work the party's predecessor in interest had or could 459 | give under the previous paragraph, plus a right to possession of the 460 | Corresponding Source of the work from the predecessor in interest, if 461 | the predecessor has it or can get it with reasonable efforts. 462 | 463 | You may not impose any further restrictions on the exercise of the 464 | rights granted or affirmed under this License. For example, you may 465 | not impose a license fee, royalty, or other charge for exercise of 466 | rights granted under this License, and you may not initiate litigation 467 | (including a cross-claim or counterclaim in a lawsuit) alleging that 468 | any patent claim is infringed by making, using, selling, offering for 469 | sale, or importing the Program or any portion of it. 470 | 471 | 11. Patents. 472 | 473 | A "contributor" is a copyright holder who authorizes use under this 474 | License of the Program or a work on which the Program is based. The 475 | work thus licensed is called the contributor's "contributor version". 476 | 477 | A contributor's "essential patent claims" are all patent claims 478 | owned or controlled by the contributor, whether already acquired or 479 | hereafter acquired, that would be infringed by some manner, permitted 480 | by this License, of making, using, or selling its contributor version, 481 | but do not include claims that would be infringed only as a 482 | consequence of further modification of the contributor version. For 483 | purposes of this definition, "control" includes the right to grant 484 | patent sublicenses in a manner consistent with the requirements of 485 | this License. 486 | 487 | Each contributor grants you a non-exclusive, worldwide, royalty-free 488 | patent license under the contributor's essential patent claims, to 489 | make, use, sell, offer for sale, import and otherwise run, modify and 490 | propagate the contents of its contributor version. 491 | 492 | In the following three paragraphs, a "patent license" is any express 493 | agreement or commitment, however denominated, not to enforce a patent 494 | (such as an express permission to practice a patent or covenant not to 495 | sue for patent infringement). To "grant" such a patent license to a 496 | party means to make such an agreement or commitment not to enforce a 497 | patent against the party. 498 | 499 | If you convey a covered work, knowingly relying on a patent license, 500 | and the Corresponding Source of the work is not available for anyone 501 | to copy, free of charge and under the terms of this License, through a 502 | publicly available network server or other readily accessible means, 503 | then you must either (1) cause the Corresponding Source to be so 504 | available, or (2) arrange to deprive yourself of the benefit of the 505 | patent license for this particular work, or (3) arrange, in a manner 506 | consistent with the requirements of this License, to extend the patent 507 | license to downstream recipients. "Knowingly relying" means you have 508 | actual knowledge that, but for the patent license, your conveying the 509 | covered work in a country, or your recipient's use of the covered work 510 | in a country, would infringe one or more identifiable patents in that 511 | country that you have reason to believe are valid. 512 | 513 | If, pursuant to or in connection with a single transaction or 514 | arrangement, you convey, or propagate by procuring conveyance of, a 515 | covered work, and grant a patent license to some of the parties 516 | receiving the covered work authorizing them to use, propagate, modify 517 | or convey a specific copy of the covered work, then the patent license 518 | you grant is automatically extended to all recipients of the covered 519 | work and works based on it. 520 | 521 | A patent license is "discriminatory" if it does not include within 522 | the scope of its coverage, prohibits the exercise of, or is 523 | conditioned on the non-exercise of one or more of the rights that are 524 | specifically granted under this License. You may not convey a covered 525 | work if you are a party to an arrangement with a third party that is 526 | in the business of distributing software, under which you make payment 527 | to the third party based on the extent of your activity of conveying 528 | the work, and under which the third party grants, to any of the 529 | parties who would receive the covered work from you, a discriminatory 530 | patent license (a) in connection with copies of the covered work 531 | conveyed by you (or copies made from those copies), or (b) primarily 532 | for and in connection with specific products or compilations that 533 | contain the covered work, unless you entered into that arrangement, 534 | or that patent license was granted, prior to 28 March 2007. 535 | 536 | Nothing in this License shall be construed as excluding or limiting 537 | any implied license or other defenses to infringement that may 538 | otherwise be available to you under applicable patent law. 539 | 540 | 12. No Surrender of Others' Freedom. 541 | 542 | If conditions are imposed on you (whether by court order, agreement or 543 | otherwise) that contradict the conditions of this License, they do not 544 | excuse you from the conditions of this License. If you cannot convey a 545 | covered work so as to satisfy simultaneously your obligations under this 546 | License and any other pertinent obligations, then as a consequence you may 547 | not convey it at all. For example, if you agree to terms that obligate you 548 | to collect a royalty for further conveying from those to whom you convey 549 | the Program, the only way you could satisfy both those terms and this 550 | License would be to refrain entirely from conveying the Program. 551 | 552 | 13. Use with the GNU Affero General Public License. 553 | 554 | Notwithstanding any other provision of this License, you have 555 | permission to link or combine any covered work with a work licensed 556 | under version 3 of the GNU Affero General Public License into a single 557 | combined work, and to convey the resulting work. The terms of this 558 | License will continue to apply to the part which is the covered work, 559 | but the special requirements of the GNU Affero General Public License, 560 | section 13, concerning interaction through a network will apply to the 561 | combination as such. 562 | 563 | 14. Revised Versions of this License. 564 | 565 | The Free Software Foundation may publish revised and/or new versions of 566 | the GNU General Public License from time to time. Such new versions will 567 | be similar in spirit to the present version, but may differ in detail to 568 | address new problems or concerns. 569 | 570 | Each version is given a distinguishing version number. If the 571 | Program specifies that a certain numbered version of the GNU General 572 | Public License "or any later version" applies to it, you have the 573 | option of following the terms and conditions either of that numbered 574 | version or of any later version published by the Free Software 575 | Foundation. If the Program does not specify a version number of the 576 | GNU General Public License, you may choose any version ever published 577 | by the Free Software Foundation. 578 | 579 | If the Program specifies that a proxy can decide which future 580 | versions of the GNU General Public License can be used, that proxy's 581 | public statement of acceptance of a version permanently authorizes you 582 | to choose that version for the Program. 583 | 584 | Later license versions may give you additional or different 585 | permissions. However, no additional obligations are imposed on any 586 | author or copyright holder as a result of your choosing to follow a 587 | later version. 588 | 589 | 15. Disclaimer of Warranty. 590 | 591 | THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY 592 | APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT 593 | HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY 594 | OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, 595 | THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 596 | PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM 597 | IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF 598 | ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 599 | 600 | 16. Limitation of Liability. 601 | 602 | IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING 603 | WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS 604 | THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY 605 | GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE 606 | USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF 607 | DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD 608 | PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), 609 | EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF 610 | SUCH DAMAGES. 611 | 612 | 17. Interpretation of Sections 15 and 16. 613 | 614 | If the disclaimer of warranty and limitation of liability provided 615 | above cannot be given local legal effect according to their terms, 616 | reviewing courts shall apply local law that most closely approximates 617 | an absolute waiver of all civil liability in connection with the 618 | Program, unless a warranty or assumption of liability accompanies a 619 | copy of the Program in return for a fee. 620 | 621 | END OF TERMS AND CONDITIONS 622 | 623 | How to Apply These Terms to Your New Programs 624 | 625 | If you develop a new program, and you want it to be of the greatest 626 | possible use to the public, the best way to achieve this is to make it 627 | free software which everyone can redistribute and change under these terms. 628 | 629 | To do so, attach the following notices to the program. It is safest 630 | to attach them to the start of each source file to most effectively 631 | state the exclusion of warranty; and each file should have at least 632 | the "copyright" line and a pointer to where the full notice is found. 633 | 634 | 635 | Copyright (C) 636 | 637 | This program is free software: you can redistribute it and/or modify 638 | it under the terms of the GNU General Public License as published by 639 | the Free Software Foundation, either version 3 of the License, or 640 | (at your option) any later version. 641 | 642 | This program is distributed in the hope that it will be useful, 643 | but WITHOUT ANY WARRANTY; without even the implied warranty of 644 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 645 | GNU General Public License for more details. 646 | 647 | You should have received a copy of the GNU General Public License 648 | along with this program. If not, see . 649 | 650 | Also add information on how to contact you by electronic and paper mail. 651 | 652 | If the program does terminal interaction, make it output a short 653 | notice like this when it starts in an interactive mode: 654 | 655 | Copyright (C) 656 | This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. 657 | This is free software, and you are welcome to redistribute it 658 | under certain conditions; type `show c' for details. 659 | 660 | The hypothetical commands `show w' and `show c' should show the appropriate 661 | parts of the General Public License. Of course, your program's commands 662 | might be different; for a GUI interface, you would use an "about box". 663 | 664 | You should also get your employer (if you work as a programmer) or school, 665 | if any, to sign a "copyright disclaimer" for the program, if necessary. 666 | For more information on this, and how to apply and follow the GNU GPL, see 667 | . 668 | 669 | The GNU General Public License does not permit incorporating your program 670 | into proprietary programs. If your program is a subroutine library, you 671 | may consider it more useful to permit linking proprietary applications with 672 | the library. If this is what you want to do, use the GNU Lesser General 673 | Public License instead of this License. But first, please read 674 | . 675 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | # Makefile for ATmegaBOOT 2 | # E.Lins, 18.7.2005 3 | # $Id$ 4 | # 5 | # Instructions 6 | # 7 | # To make bootloader .hex file: 8 | # make diecimila 9 | # make lilypad 10 | # make ng 11 | # etc... 12 | # 13 | # To burn bootloader .hex file: 14 | # make diecimila_isp 15 | # make lilypad_isp 16 | # make ng_isp 17 | # etc... 18 | # 19 | # Edit History 20 | # 201303xx: WestfW: Major Makefile restructuring. 21 | # Allows options on Make command line "make xx LED=B3" 22 | # (see also pin_defs.h) 23 | # Divide into "chip" targets and "board" targets. 24 | # Most boards are (recursive) board targets with options. 25 | # Move isp target to separate makefile (fixes m8 EFUSE) 26 | # Some (many) targets will now be rebuilt when not 27 | # strictly necessary, so that options will be included. 28 | # (any "make" with options will always compile.) 29 | # Set many variables with ?= so they can be overridden 30 | # Use arduinoISP settings as default for ISP targets 31 | # 32 | 33 | #---------------------------------------------------------------------- 34 | # 35 | # program name should not be changed... 36 | PROGRAM = optiboot 37 | 38 | # The default behavior is to build using tools that are in the users 39 | # current path variables, but we can also build using an installed 40 | # Arduino user IDE setup, or the Arduino source tree. 41 | # Uncomment this next lines to build within the arduino environment, 42 | # using the arduino-included avrgcc toolset (mac and pc) 43 | # ENV ?= arduino 44 | # ENV ?= arduinodev 45 | # OS ?= macosx 46 | # OS ?= windows 47 | 48 | # export symbols to recursive makes (for ISP) 49 | export 50 | 51 | # defaults 52 | MCU_TARGET = atmega168 53 | LDSECTIONS = -Wl,--section-start=.text=0x3e00 -Wl,--section-start=.version=0x3ffe 54 | 55 | # Build environments 56 | # Start of some ugly makefile-isms to allow optiboot to be built 57 | # in several different environments. See the README.TXT file for 58 | # details. 59 | 60 | # default 61 | fixpath = $(1) 62 | 63 | ifeq ($(ENV), arduino) 64 | # For Arduino, we assume that we're connected to the optiboot directory 65 | # included with the arduino distribution, which means that the full set 66 | # of avr-tools are "right up there" in standard places. 67 | TOOLROOT = ../../../tools 68 | GCCROOT = $(TOOLROOT)/avr/bin/ 69 | 70 | ifeq ($(OS), windows) 71 | # On windows, SOME of the tool paths will need to have backslashes instead 72 | # of forward slashes (because they use windows cmd.exe for execution instead 73 | # of a unix/mingw shell?) We also have to ensure that a consistent shell 74 | # is used even if a unix shell is installed (ie as part of WINAVR) 75 | fixpath = $(subst /,\,$1) 76 | SHELL = cmd.exe 77 | endif 78 | 79 | else ifeq ($(ENV), arduinodev) 80 | # Arduino IDE source code environment. Use the unpacked compilers created 81 | # by the build (you'll need to do "ant build" first.) 82 | ifeq ($(OS), macosx) 83 | TOOLROOT = ../../../../build/macosx/work/Arduino.app/Contents/Resources/Java/hardware/tools 84 | endif 85 | ifeq ($(OS), windows) 86 | TOOLROOT = ../../../../build/windows/work/hardware/tools 87 | endif 88 | 89 | GCCROOT = $(TOOLROOT)/avr/bin/ 90 | AVRDUDE_CONF = -C$(TOOLROOT)/avr/etc/avrdude.conf 91 | 92 | else 93 | GCCROOT = 94 | AVRDUDE_CONF = 95 | endif 96 | 97 | STK500 = "C:\Program Files\Atmel\AVR Tools\STK500\Stk500.exe" 98 | STK500-1 = $(STK500) -e -d$(MCU_TARGET) -pf -vf -if$(PROGRAM)_$(TARGET).hex \ 99 | -lFF -LFF -f$(HFUSE)$(LFUSE) -EF8 -ms -q -cUSB -I200kHz -s -wt 100 | STK500-2 = $(STK500) -d$(MCU_TARGET) -ms -q -lCF -LCF -cUSB -I200kHz -s -wt 101 | # 102 | # End of build environment code. 103 | 104 | 105 | OBJ = $(PROGRAM).o 106 | OPTIMIZE = -Os -fno-inline-small-functions -fno-split-wide-types -mrelax 107 | 108 | DEFS = 109 | LIBS = 110 | 111 | CC = $(GCCROOT)avr-gcc 112 | 113 | # Override is only needed by avr-lib build system. 114 | 115 | override CFLAGS = -g -Wall $(OPTIMIZE) -mmcu=$(MCU_TARGET) -DF_CPU=$(AVR_FREQ) $(DEFS) 116 | override LDFLAGS = $(LDSECTIONS) -Wl,--relax -nostartfiles -nostdlib 117 | #-Wl,--gc-sections 118 | 119 | OBJCOPY = $(GCCROOT)avr-objcopy 120 | OBJDUMP = $(call fixpath,$(GCCROOT)avr-objdump) 121 | 122 | SIZE = $(GCCROOT)avr-size 123 | 124 | # 125 | # Make command-line Options. 126 | # Permit commands like "make atmega328 LED_START_FLASHES=10" to pass the 127 | # appropriate parameters ("-DLED_START_FLASHES=10") to gcc 128 | # 129 | 130 | ifdef BAUD_RATE 131 | BAUD_RATE_CMD = -DBAUD_RATE=$(BAUD_RATE) 132 | dummy = FORCE 133 | else 134 | BAUD_RATE_CMD = -DBAUD_RATE=115200 135 | endif 136 | 137 | ifdef LED_START_FLASHES 138 | LED_START_FLASHES_CMD = -DLED_START_FLASHES=$(LED_START_FLASHES) 139 | dummy = FORCE 140 | else 141 | LED_START_FLASHES_CMD = -DLED_START_FLASHES=3 142 | endif 143 | 144 | # BIG_BOOT: Include extra features, up to 1K. 145 | ifdef BIGBOOT 146 | BIGBOOT_CMD = -DBIGBOOT=1 147 | dummy = FORCE 148 | endif 149 | 150 | ifdef SOFT_UART 151 | SOFT_UART_CMD = -DSOFT_UART=1 152 | dummy = FORCE 153 | endif 154 | 155 | ifdef LED_DATA_FLASH 156 | LED_DATA_FLASH_CMD = -DLED_DATA_FLASH=1 157 | dummy = FORCE 158 | endif 159 | 160 | ifdef LED 161 | LED_CMD = -DLED=$(LED) 162 | dummy = FORCE 163 | endif 164 | 165 | ifdef SINGLESPEED 166 | SSCMD = -DSINGLESPEED=1 167 | endif 168 | 169 | COMMON_OPTIONS = $(BAUD_RATE_CMD) $(LED_START_FLASHES_CMD) $(BIGBOOT_CMD) 170 | COMMON_OPTIONS += $(SOFT_UART_CMD) $(LED_DATA_FLASH_CMD) $(LED_CMD) $(SSCMD) 171 | 172 | #UART is handled separately and only passed for devices with more than one. 173 | ifdef UART 174 | UARTCMD = -DUART=$(UART) 175 | endif 176 | 177 | # Not supported yet 178 | # ifdef SUPPORT_EEPROM 179 | # SUPPORT_EEPROM_CMD = -DSUPPORT_EEPROM 180 | # dummy = FORCE 181 | # endif 182 | 183 | # Not supported yet 184 | # ifdef TIMEOUT_MS 185 | # TIMEOUT_MS_CMD = -DTIMEOUT_MS=$(TIMEOUT_MS) 186 | # dummy = FORCE 187 | # endif 188 | # 189 | 190 | #--------------------------------------------------------------------------- 191 | # "Chip-level Platform" targets. 192 | # A "Chip-level Platform" compiles for a particular chip, but probably does 193 | # not have "standard" values for things like clock speed, LED pin, etc. 194 | # Makes for chip-level platforms should usually explicitly define their 195 | # options like: "make atmega1285 AVR_FREQ=16000000L LED=D0" 196 | #--------------------------------------------------------------------------- 197 | # 198 | # Note about fuses: 199 | # the efuse should really be 0xf8; since, however, only the lower 200 | # three bits of that byte are used on the atmega168, avrdude gets 201 | # confused if you specify 1's for the higher bits, see: 202 | # http://tinker.it/now/2007/02/24/the-tale-of-avrdude-atmega168-and-extended-bits-fuses/ 203 | # 204 | # similarly, the lock bits should be 0xff instead of 0x3f (to 205 | # unlock the bootloader section) and 0xcf instead of 0x2f (to 206 | # lock it), but since the high two bits of the lock byte are 207 | # unused, avrdude would get confused. 208 | #--------------------------------------------------------------------------- 209 | # 210 | 211 | # Test platforms 212 | # Virtual boot block test 213 | virboot328: TARGET = atmega328 214 | virboot328: MCU_TARGET = atmega328p 215 | virboot328: CFLAGS += $(COMMON_OPTIONS) '-DVIRTUAL_BOOT' 216 | virboot328: AVR_FREQ ?= 16000000L 217 | virboot328: LDSECTIONS = -Wl,--section-start=.text=0x7e00 -Wl,--section-start=.version=0x7ffe 218 | virboot328: $(PROGRAM)_atmega328.hex 219 | virboot328: $(PROGRAM)_atmega328.lst 220 | 221 | # Diecimila, Duemilanove with m168, and NG use identical bootloaders 222 | # Call it "atmega168" for generality and clarity, keep "diecimila" for 223 | # backward compatibility of makefile 224 | # 225 | atmega168: TARGET = atmega168 226 | atmega168: MCU_TARGET = atmega168 227 | atmega168: CFLAGS += $(COMMON_OPTIONS) 228 | atmega168: AVR_FREQ ?= 16000000L 229 | atmega168: $(PROGRAM)_atmega168.hex 230 | atmega168: $(PROGRAM)_atmega168.lst 231 | 232 | atmega168_isp: atmega168 233 | atmega168_isp: TARGET = atmega168 234 | # 2.7V brownout 235 | atmega168_isp: HFUSE ?= DD 236 | # Low power xtal (16MHz) 16KCK/14CK+65ms 237 | atmega168_isp: LFUSE ?= FF 238 | # 512 byte boot 239 | atmega168_isp: EFUSE ?= 04 240 | atmega168_isp: isp 241 | 242 | atmega328: TARGET = atmega328 243 | atmega328: MCU_TARGET = atmega328p 244 | atmega328: CFLAGS += $(COMMON_OPTIONS) 245 | atmega328: AVR_FREQ ?= 16000000L 246 | atmega328: LDSECTIONS = -Wl,--section-start=.text=0x7c00 -Wl,--section-start=.version=0x7ffe 247 | atmega328: $(PROGRAM)_atmega328.hex 248 | atmega328: $(PROGRAM)_atmega328.lst 249 | 250 | atmega328_isp: atmega328 251 | atmega328_isp: TARGET = atmega328 252 | atmega328_isp: MCU_TARGET = atmega328p 253 | # 512 byte boot, SPIEN 254 | atmega328_isp: HFUSE ?= DE 255 | # Low power xtal (16MHz) 16KCK/14CK+65ms 256 | atmega328_isp: LFUSE ?= FF 257 | # 2.7V brownout 258 | atmega328_isp: EFUSE ?= FD 259 | atmega328_isp: isp 260 | 261 | atmega644p: TARGET = atmega644p 262 | atmega644p: MCU_TARGET = atmega644p 263 | atmega644p: CFLAGS += $(COMMON_OPTIONS) -DBIGBOOT $(LED_CMD) 264 | atmega644p: AVR_FREQ ?= 16000000L 265 | atmega644p: LDSECTIONS = -Wl,--section-start=.text=0xfc00 -Wl,--section-start=.version=0xfffe 266 | atmega644p: CFLAGS += $(UARTCMD) 267 | atmega644p: $(PROGRAM)_atmega644p.hex 268 | atmega644p: $(PROGRAM)_atmega644p.lst 269 | 270 | atmega1284: TARGET = atmega1284p 271 | atmega1284: MCU_TARGET = atmega1284p 272 | atmega1284: CFLAGS += $(COMMON_OPTIONS) -DBIGBOOT $(LED_CMD) 273 | atmega1284: AVR_FREQ ?= 16000000L 274 | atmega1284: LDSECTIONS = -Wl,--section-start=.text=0x1fc00 -Wl,--section-start=.version=0x1fffe 275 | atmega1284: CFLAGS += $(UARTCMD) 276 | atmega1284: $(PROGRAM)_atmega1284p.hex 277 | atmega1284: $(PROGRAM)_atmega1284p.lst 278 | 279 | atmega1284p: atmega1284 280 | 281 | atmega1284_isp: atmega1284 282 | atmega1284_isp: TARGET = atmega1284p 283 | atmega1284_isp: MCU_TARGET = atmega1284p 284 | # 1024 byte boot 285 | atmega1284_isp: HFUSE ?= DE 286 | # Full Swing xtal (16MHz) 16KCK/14CK+65ms 287 | atmega1284_isp: LFUSE ?= F7 288 | # 2.7V brownout 289 | atmega1284_isp: EFUSE ?= FD 290 | atmega1284_isp: isp 291 | 292 | #Atmega1280 293 | atmega1280: MCU_TARGET = atmega1280 294 | atmega1280: CFLAGS += $(COMMON_OPTIONS) -DBIGBOOT $(UART_CMD) 295 | atmega1280: AVR_FREQ ?= 16000000L 296 | atmega1280: LDSECTIONS = -Wl,--section-start=.text=0x1fc00 -Wl,--section-start=.version=0x1fffe 297 | atmega1280: $(PROGRAM)_atmega1280.hex 298 | atmega1280: $(PROGRAM)_atmega1280.lst 299 | 300 | 301 | # ATmega8 302 | # 303 | atmega8: TARGET = atmega8 304 | atmega8: MCU_TARGET = atmega8 305 | atmega8: CFLAGS += $(COMMON_OPTIONS) 306 | atmega8: AVR_FREQ ?= 16000000L 307 | atmega8: LDSECTIONS = -Wl,--section-start=.text=0x1e00 -Wl,--section-start=.version=0x1ffe 308 | atmega8: $(PROGRAM)_atmega8.hex 309 | atmega8: $(PROGRAM)_atmega8.lst 310 | 311 | atmega8_isp: atmega8 312 | atmega8_isp: TARGET = atmega8 313 | atmega8_isp: MCU_TARGET = atmega8 314 | # SPIEN, CKOPT (for full swing xtal), Bootsize=512B 315 | atmega8_isp: HFUSE ?= CC 316 | # 2.7V brownout, 16MHz Xtal, 16KCK/14CK+65ms 317 | atmega8_isp: LFUSE ?= BF 318 | atmega8_isp: isp 319 | 320 | # ATmega88 321 | # 322 | atmega88: TARGET = atmega88 323 | atmega88: MCU_TARGET = atmega88 324 | atmega88: CFLAGS += $(COMMON_OPTIONS) 325 | atmega88: AVR_FREQ ?= 16000000L 326 | atmega88: LDSECTIONS = -Wl,--section-start=.text=0x1e00 -Wl,--section-start=.version=0x1ffe 327 | atmega88: $(PROGRAM)_atmega88.hex 328 | atmega88: $(PROGRAM)_atmega88.lst 329 | 330 | atmega88_isp: atmega88 331 | atmega88_isp: TARGET = atmega88 332 | atmega88_isp: MCU_TARGET = atmega88 333 | # 2.7V brownout 334 | atmega88_isp: HFUSE ?= DD 335 | # Low power xtal (16MHz) 16KCK/14CK+65ms 336 | atemga88_isp: LFUSE ?= FF 337 | # 512 byte boot 338 | atmega88_isp: EFUSE ?= 04 339 | atmega88_isp: isp 340 | 341 | atmega32: TARGET = atmega32 342 | atmega32: MCU_TARGET = atmega32 343 | atmega32: CFLAGS += $(COMMON_OPTIONS) 344 | atmega32: AVR_FREQ ?= 11059200L 345 | atmega32: LDSECTIONS = -Wl,--section-start=.text=0x7e00 -Wl,--section-start=.version=0x7ffe 346 | atmega32: $(PROGRAM)_atmega32.hex 347 | atmega32: $(PROGRAM)_atmega32.lst 348 | 349 | atmega32_isp: atmega32 350 | atmega32_isp: TARGET = atmega32 351 | atmega32_isp: MCU_TARGET = atmega32 352 | # No OCD or JTAG, SPIEN, CKOPT (for full swing xtal), Bootsize=512B 353 | atmega32_isp: HFUSE ?= CE 354 | # 2.7V brownout, 16MHz Xtal, 16KCK/14CK+65ms 355 | atemga32_isp: LFUSE ?= BF 356 | atmega32_isp: isp 357 | 358 | 359 | 360 | #--------------------------------------------------------------------------- 361 | # "Board-level Platform" targets. 362 | # A "Board-level Platform" implies a manufactured platform with a particular 363 | # AVR_FREQ, LED, and so on. Parameters are not particularly changable from 364 | # the "make" command line. 365 | # Most of the board-level platform builds should envoke make recursively 366 | # appropriate specific options 367 | #--------------------------------------------------------------------------- 368 | # 20MHz clocked platforms 369 | # 370 | # These are capable of 230400 baud, or 115200 baud on PC (Arduino Avrdude issue) 371 | # 372 | 373 | pro20: TARGET = pro_20mhz 374 | pro20: CHIP = atmega168 375 | pro20: 376 | $(MAKE) atmega168 AVR_FREQ=20000000L LED_START_FLASHES=3 377 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 378 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 379 | 380 | pro20_isp: pro20 381 | pro20_isp: TARGET = pro_20mhz 382 | # 2.7V brownout 383 | pro20_isp: HFUSE ?= DD 384 | # Full swing xtal (20MHz) 258CK/14CK+4.1ms 385 | pro20_isp: LFUSE ?= C6 386 | # 512 byte boot 387 | pro20_isp: EFUSE ?= 04 388 | pro20_isp: isp 389 | 390 | # 16MHz clocked platforms 391 | # 392 | # These are capable of 230400 baud, or 115200 baud on PC (Arduino Avrdude issue) 393 | # 394 | 395 | pro16: TARGET = pro_16MHz 396 | pro16: CHIP = atmega168 397 | pro16: 398 | $(MAKE) $(CHIP) AVR_FREQ=16000000L LED_START_FLASHES=3 399 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 400 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 401 | 402 | pro16_isp: pro16 403 | pro16_isp: TARGET = pro_16MHz 404 | # 2.7V brownout 405 | pro16_isp: HFUSE ?= DD 406 | # Full swing xtal (20MHz) 258CK/14CK+4.1ms 407 | pro16_isp: LFUSE ?= C6 408 | # 512 byte boot 409 | pro16_isp: EFUSE ?= 04 410 | pro16_isp: isp 411 | 412 | diecimila: TARGET = diecimila 413 | diecimila: CHIP = atmega168 414 | diecimila: 415 | $(MAKE) $(CHIP) AVR_FREQ=16000000L LED_START_FLASHES=3 416 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 417 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 418 | 419 | diecimila_isp: diecimila 420 | diecimila_isp: TARGET = diecimila 421 | # 2.7V brownout 422 | diecimila_isp: HFUSE ?= DD 423 | # Low power xtal (16MHz) 16KCK/14CK+65ms 424 | diecimila_isp: LFUSE ?= FF 425 | # 512 byte boot 426 | diecimila_isp: EFUSE ?= 04 427 | diecimila_isp: isp 428 | 429 | # Sanguino has a minimum boot size of 1024 bytes, so enable extra functions 430 | # 431 | sanguino: TARGET = $@ 432 | sanguino: CHIP = atmega644p 433 | sanguino: 434 | $(MAKE) $(CHIP) AVR_FREQ=16000000L LED=B0 435 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 436 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 437 | 438 | sanguino_isp: sanguino 439 | sanguino_isp: TARGET = sanguino 440 | sanguino_isp: MCU_TARGET = atmega644p 441 | # 1024 byte boot 442 | sanguino_isp: HFUSE ?= DE 443 | # Full swing xtal (16MHz) 16KCK/14CK+65ms 444 | sanguino_isp: LFUSE ?= F7 445 | # 2.7V brownout 446 | sanguino_isp: EFUSE ?= FD 447 | sanguino_isp: isp 448 | 449 | mighty1284: TARGET = $@ 450 | mighty1284: CHIP = atmega1284p 451 | mighty1284: 452 | $(MAKE) $(CHIP) AVR_FREQ=16000000L LED=D7 453 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 454 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 455 | 456 | mighty1284_isp: mighty1284 457 | mighty1284_isp: TARGET = mighty1284 458 | mighty1284_isp: MCU_TARGET = atmega1284p 459 | # 1024 byte boot 460 | mighty1284_isp: HFUSE ?= DE 461 | # Full swing xtal (16MHz) 16KCK/14CK+65ms 462 | mighty1284_isp: LFUSE ?= F7 463 | # 2.7V brownout 464 | mighty1284_isp: EFUSE ?= FD 465 | mighty1284_isp: isp 466 | 467 | bobuino: TARGET = $@ 468 | bobuino: CHIP = atmega1284p 469 | bobuino: 470 | $(MAKE) $(CHIP) AVR_FREQ=16000000L LED=B5 471 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 472 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 473 | 474 | bobuino_isp: bobuino 475 | bobuino_isp: TARGET = bobuino 476 | bobuino_isp: MCU_TARGET = atmega1284p 477 | # 1024 byte boot 478 | bobuino_isp: HFUSE ?= DE 479 | # Full swing xtal (16MHz) 16KCK/14CK+65ms 480 | bobuino_isp: LFUSE ?= F7 481 | # 2.7V brownout 482 | bobuino_isp: EFUSE ?= FD 483 | bobuino_isp: isp 484 | 485 | # MEGA1280 Board (this is different from the atmega1280 chip platform) 486 | # Mega has a minimum boot size of 1024 bytes, so enable extra functions 487 | # Note that optiboot does not (can not) work on the MEGA2560 488 | #mega: TARGET = atmega1280 489 | mega1280: atmega1280 490 | 491 | 492 | mega1280_isp: mega1280 493 | mega1280_isp: TARGET = atmega1280 494 | mega1280_isp: MCU_TARGET = atmega1280 495 | # 1024 byte boot 496 | mega1280_isp: HFUSE ?= DE 497 | # Low power xtal (16MHz) 16KCK/14CK+65ms 498 | mega1280_isp: LFUSE ?= FF 499 | # 2.7V brownout; wants F5 for some reason... 500 | mega1280_isp: EFUSE ?= F5 501 | mega1280_isp: isp 502 | 503 | # 8MHz clocked platforms 504 | # 505 | # These are capable of 115200 baud 506 | # Note that "new" Arduinos with an AVR as USB/Serial converter will NOT work 507 | # with an 8MHz target Arduino. The bitrate errors are in opposite directions, 508 | # and total too large a number. 509 | # 510 | 511 | lilypad: TARGET = $@ 512 | lilypad: CHIP = atmega168 513 | lilypad: 514 | $(MAKE) $(CHIP) AVR_FREQ=8000000L LED_START_FLASHES=3 515 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 516 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 517 | 518 | lilypad_isp: lilypad 519 | lilypad_isp: TARGET = lilypad 520 | # 2.7V brownout 521 | lilypad_isp: HFUSE ?= DD 522 | # Internal 8MHz osc (8MHz) Slow rising power 523 | lilypad_isp: LFUSE ?= E2 524 | # 512 byte boot 525 | lilypad_isp: EFUSE ?= 04 526 | lilypad_isp: isp 527 | 528 | # lilypad_resonator is the same as a 8MHz lilypad, except for fuses. 529 | lilypad_resonator: lilypad 530 | 531 | lilypad_resonator_isp: lilypad 532 | lilypad_resonator_isp: TARGET = lilypad 533 | # 2.7V brownout 534 | lilypad_resonator_isp: HFUSE ?= DD 535 | # Full swing xtal (20MHz) 258CK/14CK+4.1ms 536 | lilypad_resonator_isp: LFUSE ?= C6 537 | # 512 byte boot 538 | lilypad_resonator_isp: EFUSE ?= 04 539 | lilypad_resonator_isp: isp 540 | 541 | pro8: TARGET = pro_8MHz 542 | pro8: CHIP = atmega328 543 | pro8: 544 | $(MAKE) $(CHIP) AVR_FREQ=8000000L LED_START_FLASHES=3 545 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 546 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 547 | 548 | pro8_isp: pro8 549 | pro8_isp: TARGET = pro_8MHz 550 | # 2.7V brownout 551 | pro8_isp: HFUSE ?= DD 552 | # Full swing xtal (20MHz) 258CK/14CK+4.1ms 553 | pro8_isp: LFUSE ?= C6 554 | # 512 byte boot 555 | pro8_isp: EFUSE ?= 04 556 | pro8_isp: isp 557 | 558 | atmega328_pro8: TARGET = atmega328_pro_8MHz 559 | atmega328_pro8: CHIP = atmega328 560 | atmega328_pro8: 561 | $(MAKE) $(CHIP) AVR_FREQ=8000000L LED_START_FLASHES=3 562 | mv $(PROGRAM)_$(CHIP).hex $(PROGRAM)_$(TARGET).hex 563 | mv $(PROGRAM)_$(CHIP).lst $(PROGRAM)_$(TARGET).lst 564 | 565 | atmega328_pro8_isp: atmega328_pro8 566 | atmega328_pro8_isp: TARGET = atmega328_pro_8MHz 567 | atmega328_pro8_isp: MCU_TARGET = atmega328p 568 | # 512 byte boot, SPIEN 569 | atmega328_pro8_isp: HFUSE ?= DE 570 | # Low power xtal (16MHz) 16KCK/14CK+65ms 571 | atmega328_pro8_isp: LFUSE ?= FF 572 | # 2.7V brownout 573 | atmega328_pro8_isp: EFUSE ?= DE 574 | atmega328_pro8_isp: isp 575 | 576 | mysensor_micro: atmega328_pro8 577 | mysensor_micro: target = atmega_pro_8MHz 578 | mysensor_micro: MCU_TARGET = atmega328p 579 | # 512 byte boot, SPIEN 580 | mysensor_micro: HFUSE ?= DE 581 | # Low power xtal (16MHz) 16KCK/14CK+65ms 582 | mysensor_micro: LFUSE ?= FF 583 | # 2.7V brownout 584 | mysensor_micro: EFUSE ?= DE 585 | mysensor_micro: LED=C3 586 | mysensor_micro: BAUD_RATE=57600 587 | 588 | # 1MHz clocked platforms 589 | # 590 | # These are capable of 9600 baud 591 | # 592 | 593 | luminet: TARGET = luminet 594 | luminet: MCU_TARGET = attiny84 595 | luminet: CFLAGS += $(COMMON_OPTIONS) '-DSOFT_UART' '-DBAUD_RATE=9600' 596 | luminet: CFLAGS += '-DVIRTUAL_BOOT_PARTITION' 597 | luminet: AVR_FREQ ?= 1000000L 598 | luminet: LDSECTIONS = -Wl,--section-start=.text=0x1d00 -Wl,--section-start=.version=0x1efe 599 | luminet: $(PROGRAM)_luminet.hex 600 | luminet: $(PROGRAM)_luminet.lst 601 | 602 | luminet_isp: luminet 603 | luminet_isp: TARGET = luminet 604 | luminet_isp: MCU_TARGET = attiny84 605 | # Brownout disabled 606 | luminet_isp: HFUSE ?= DF 607 | # 1MHz internal oscillator, slowly rising power 608 | luminet_isp: LFUSE ?= 62 609 | # Self-programming enable 610 | luminet_isp: EFUSE ?= FE 611 | luminet_isp: isp 612 | 613 | 614 | #--------------------------------------------------------------------------- 615 | # 616 | # Generic build instructions 617 | # 618 | 619 | FORCE: 620 | 621 | baudcheck: FORCE 622 | - @$(CC) $(CFLAGS) -E baudcheck.c -o baudcheck.tmp.sh 623 | - @sh baudcheck.tmp.sh 624 | 625 | isp: $(TARGET) 626 | $(MAKE) -f Makefile.isp isp TARGET=$(TARGET) 627 | 628 | isp-stk500: $(PROGRAM)_$(TARGET).hex 629 | $(STK500-1) 630 | $(STK500-2) 631 | 632 | %.elf: $(OBJ) $(dummy) 633 | $(CC) $(CFLAGS) $(LDFLAGS) -o $@ $< $(LIBS) 634 | $(SIZE) $@ 635 | 636 | clean: 637 | rm -rf *.o *.elf *.lst *.map *.sym *.lss *.eep *.srec *.bin *.hex *.tmp.sh 638 | 639 | %.lst: %.elf 640 | $(OBJDUMP) -h -S $< > $@ 641 | 642 | %.hex: %.elf 643 | $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O ihex $< $@ 644 | 645 | %.srec: %.elf 646 | $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O srec $< $@ 647 | 648 | %.bin: %.elf 649 | $(OBJCOPY) -j .text -j .data -j .version --set-section-flags .version=alloc,load -O binary $< $@ 650 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | DualOptiboot 2 | ============ 3 | 4 | Custom Optiboot to add wireless programming capability to Moteino 5 | Copyright Felix Rusu (2013-2014), felix@lowpowerlab.com 6 | More at: http://lowpowerlab.com/Moteino 7 | 8 | This Optiboot version is modified to add the capability of reflashing 9 | from an external SPI flash memory chip. As configured this will work 10 | with Moteino (www.lowpowerlab.com/Moteino) provided a SPI flash chip 11 | is present on the dedicated onboard footprint. 12 | Summary of how this Optiboot version works: 13 | - it looks for an external flash chip 14 | - if one is found (SPI returns valid data) it will further look 15 | for a new sketch flash image signature and size 16 | starting at address 0: FLXIMG:9999:XXXXXXXXXXX 17 | where: - 'FLXIMG' is fixed signature indicating FLASH chip 18 | contains a valid new flash image to be burned 19 | - '9999' are 4 size bytes indicating how long the 20 | new flash image is (how many bytes to read) 21 | - 'XXXXXX' are the de-hexified bytes of the flash 22 | pages to be burned 23 | - ':' colons have fixed positions (delimiters) 24 | - if no valid signature/size are found, it will skip and 25 | function as it normally would (listen to STK500 protocol on serial port) 26 | 27 | The added code will result in a compiled size of just under 1kb 28 | (Originally Optiboot takes just under 0.5kb) 29 | 30 | ------------------------------------------------------------------------------------------------------------- 31 | 32 | To compile copy the Optiboot.c and Makefile files where Optiboot is originally located, mine is at: 33 | arduino-install-dir\hardware\arduino\bootloaders\optiboot\ 34 | Backup the original files andbefore overwrite both files. 35 | Then compile by running: 36 | make atmega328 37 | make atmega1284p 38 | 39 | ##License 40 | GPL 3.0. See License.txt file. -------------------------------------------------------------------------------- /boot.h: -------------------------------------------------------------------------------- 1 | /* Modified to use out for SPM access 2 | ** Peter Knight, Optiboot project http://optiboot.googlecode.com 3 | ** 4 | ** Todo: Tidy up 5 | ** 6 | ** "_short" routines execute 1 cycle faster and use 1 less word of flash 7 | ** by using "out" instruction instead of "sts". 8 | ** 9 | ** Additional elpm variants that trust the value of RAMPZ 10 | */ 11 | 12 | /* Copyright (c) 2002, 2003, 2004, 2005, 2006, 2007 Eric B. Weddington 13 | All rights reserved. 14 | 15 | Redistribution and use in source and binary forms, with or without 16 | modification, are permitted provided that the following conditions are met: 17 | 18 | * Redistributions of source code must retain the above copyright 19 | notice, this list of conditions and the following disclaimer. 20 | * Redistributions in binary form must reproduce the above copyright 21 | notice, this list of conditions and the following disclaimer in 22 | the documentation and/or other materials provided with the 23 | distribution. 24 | * Neither the name of the copyright holders nor the names of 25 | contributors may be used to endorse or promote products derived 26 | from this software without specific prior written permission. 27 | 28 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 29 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 30 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 31 | ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 32 | LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 33 | CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 34 | SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 35 | INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 36 | CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 37 | ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 38 | POSSIBILITY OF SUCH DAMAGE. */ 39 | 40 | /* $Id: boot.h,v 1.27.2.3 2008/09/30 13:58:48 arcanum Exp $ */ 41 | 42 | #ifndef _AVR_BOOT_H_ 43 | #define _AVR_BOOT_H_ 1 44 | 45 | /** \file */ 46 | /** \defgroup avr_boot : Bootloader Support Utilities 47 | \code 48 | #include 49 | #include 50 | \endcode 51 | 52 | The macros in this module provide a C language interface to the 53 | bootloader support functionality of certain AVR processors. These 54 | macros are designed to work with all sizes of flash memory. 55 | 56 | Global interrupts are not automatically disabled for these macros. It 57 | is left up to the programmer to do this. See the code example below. 58 | Also see the processor datasheet for caveats on having global interrupts 59 | enabled during writing of the Flash. 60 | 61 | \note Not all AVR processors provide bootloader support. See your 62 | processor datasheet to see if it provides bootloader support. 63 | 64 | \todo From email with Marek: On smaller devices (all except ATmega64/128), 65 | __SPM_REG is in the I/O space, accessible with the shorter "in" and "out" 66 | instructions - since the boot loader has a limited size, this could be an 67 | important optimization. 68 | 69 | \par API Usage Example 70 | The following code shows typical usage of the boot API. 71 | 72 | \code 73 | #include 74 | #include 75 | #include 76 | 77 | void boot_program_page (uint32_t page, uint8_t *buf) 78 | { 79 | uint16_t i; 80 | uint8_t sreg; 81 | 82 | // Disable interrupts. 83 | 84 | sreg = SREG; 85 | cli(); 86 | 87 | eeprom_busy_wait (); 88 | 89 | boot_page_erase (page); 90 | boot_spm_busy_wait (); // Wait until the memory is erased. 91 | 92 | for (i=0; i 116 | #include 117 | #include 118 | #include 119 | 120 | /* Check for SPM Control Register in processor. */ 121 | #if defined (SPMCSR) 122 | # define __SPM_REG SPMCSR 123 | #elif defined (SPMCR) 124 | # define __SPM_REG SPMCR 125 | #else 126 | # error AVR processor does not provide bootloader support! 127 | #endif 128 | 129 | 130 | /* Check for SPM Enable bit. */ 131 | #if defined(SPMEN) 132 | # define __SPM_ENABLE SPMEN 133 | #elif defined(SELFPRGEN) 134 | # define __SPM_ENABLE SELFPRGEN 135 | #else 136 | # error Cannot find SPM Enable bit definition! 137 | #endif 138 | 139 | /** \ingroup avr_boot 140 | \def BOOTLOADER_SECTION 141 | 142 | Used to declare a function or variable to be placed into a 143 | new section called .bootloader. This section and its contents 144 | can then be relocated to any address (such as the bootloader 145 | NRWW area) at link-time. */ 146 | 147 | #define BOOTLOADER_SECTION __attribute__ ((section (".bootloader"))) 148 | 149 | /* Create common bit definitions. */ 150 | #ifdef ASB 151 | #define __COMMON_ASB ASB 152 | #else 153 | #define __COMMON_ASB RWWSB 154 | #endif 155 | 156 | #ifdef ASRE 157 | #define __COMMON_ASRE ASRE 158 | #else 159 | #define __COMMON_ASRE RWWSRE 160 | #endif 161 | 162 | /* Define the bit positions of the Boot Lock Bits. */ 163 | 164 | #define BLB12 5 165 | #define BLB11 4 166 | #define BLB02 3 167 | #define BLB01 2 168 | 169 | /** \ingroup avr_boot 170 | \def boot_spm_interrupt_enable() 171 | Enable the SPM interrupt. */ 172 | 173 | #define boot_spm_interrupt_enable() (__SPM_REG |= (uint8_t)_BV(SPMIE)) 174 | 175 | /** \ingroup avr_boot 176 | \def boot_spm_interrupt_disable() 177 | Disable the SPM interrupt. */ 178 | 179 | #define boot_spm_interrupt_disable() (__SPM_REG &= (uint8_t)~_BV(SPMIE)) 180 | 181 | /** \ingroup avr_boot 182 | \def boot_is_spm_interrupt() 183 | Check if the SPM interrupt is enabled. */ 184 | 185 | #define boot_is_spm_interrupt() (__SPM_REG & (uint8_t)_BV(SPMIE)) 186 | 187 | /** \ingroup avr_boot 188 | \def boot_rww_busy() 189 | Check if the RWW section is busy. */ 190 | 191 | #define boot_rww_busy() (__SPM_REG & (uint8_t)_BV(__COMMON_ASB)) 192 | 193 | /** \ingroup avr_boot 194 | \def boot_spm_busy() 195 | Check if the SPM instruction is busy. */ 196 | 197 | #define boot_spm_busy() (__SPM_REG & (uint8_t)_BV(__SPM_ENABLE)) 198 | 199 | /** \ingroup avr_boot 200 | \def boot_spm_busy_wait() 201 | Wait while the SPM instruction is busy. */ 202 | 203 | #define boot_spm_busy_wait() do{}while(boot_spm_busy()) 204 | 205 | #define __BOOT_PAGE_ERASE (_BV(__SPM_ENABLE) | _BV(PGERS)) 206 | #define __BOOT_PAGE_WRITE (_BV(__SPM_ENABLE) | _BV(PGWRT)) 207 | #define __BOOT_PAGE_FILL _BV(__SPM_ENABLE) 208 | #define __BOOT_RWW_ENABLE (_BV(__SPM_ENABLE) | _BV(__COMMON_ASRE)) 209 | #define __BOOT_LOCK_BITS_SET (_BV(__SPM_ENABLE) | _BV(BLBSET)) 210 | 211 | #define __boot_page_fill_short(address, data) \ 212 | (__extension__({ \ 213 | __asm__ __volatile__ \ 214 | ( \ 215 | "movw r0, %3\n\t" \ 216 | "out %0, %1\n\t" \ 217 | "spm\n\t" \ 218 | "clr r1\n\t" \ 219 | : \ 220 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 221 | "r" ((uint8_t)__BOOT_PAGE_FILL), \ 222 | "z" ((uint16_t)address), \ 223 | "r" ((uint16_t)data) \ 224 | : "r0" \ 225 | ); \ 226 | })) 227 | 228 | #define __boot_page_fill_normal(address, data) \ 229 | (__extension__({ \ 230 | __asm__ __volatile__ \ 231 | ( \ 232 | "movw r0, %3\n\t" \ 233 | "sts %0, %1\n\t" \ 234 | "spm\n\t" \ 235 | "clr r1\n\t" \ 236 | : \ 237 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 238 | "r" ((uint8_t)__BOOT_PAGE_FILL), \ 239 | "z" ((uint16_t)address), \ 240 | "r" ((uint16_t)data) \ 241 | : "r0" \ 242 | ); \ 243 | })) 244 | 245 | #define __boot_page_fill_alternate(address, data)\ 246 | (__extension__({ \ 247 | __asm__ __volatile__ \ 248 | ( \ 249 | "movw r0, %3\n\t" \ 250 | "sts %0, %1\n\t" \ 251 | "spm\n\t" \ 252 | ".word 0xffff\n\t" \ 253 | "nop\n\t" \ 254 | "clr r1\n\t" \ 255 | : \ 256 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 257 | "r" ((uint8_t)__BOOT_PAGE_FILL), \ 258 | "z" ((uint16_t)address), \ 259 | "r" ((uint16_t)data) \ 260 | : "r0" \ 261 | ); \ 262 | })) 263 | 264 | #define __boot_page_fill_extended(address, data) \ 265 | (__extension__({ \ 266 | __asm__ __volatile__ \ 267 | ( \ 268 | "movw r0, %4\n\t" \ 269 | "movw r30, %A3\n\t" \ 270 | "sts %1, %C3\n\t" \ 271 | "sts %0, %2\n\t" \ 272 | "spm\n\t" \ 273 | "clr r1\n\t" \ 274 | : \ 275 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 276 | "i" (_SFR_MEM_ADDR(RAMPZ)), \ 277 | "r" ((uint8_t)__BOOT_PAGE_FILL), \ 278 | "r" ((uint32_t)address), \ 279 | "r" ((uint16_t)data) \ 280 | : "r0", "r30", "r31" \ 281 | ); \ 282 | })) 283 | 284 | #define __boot_page_fill_extended_short(address, data) \ 285 | (__extension__({ \ 286 | __asm__ __volatile__ \ 287 | ( \ 288 | "movw r0, %4\n\t" \ 289 | "movw r30, %A3\n\t" \ 290 | "out %1, %C3\n\t" \ 291 | "out %0, %2\n\t" \ 292 | "spm\n\t" \ 293 | "clr r1\n\t" \ 294 | : \ 295 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 296 | "i" (_SFR_IO_ADDR(RAMPZ)), \ 297 | "r" ((uint8_t)__BOOT_PAGE_FILL), \ 298 | "r" ((uint32_t)address), \ 299 | "r" ((uint16_t)data) \ 300 | : "r0", "r30", "r31" \ 301 | ); \ 302 | })) 303 | 304 | #define __boot_page_erase_short(address) \ 305 | (__extension__({ \ 306 | __asm__ __volatile__ \ 307 | ( \ 308 | "out %0, %1\n\t" \ 309 | "spm\n\t" \ 310 | : \ 311 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 312 | "r" ((uint8_t)__BOOT_PAGE_ERASE), \ 313 | "z" ((uint16_t)address) \ 314 | ); \ 315 | })) 316 | 317 | 318 | #define __boot_page_erase_normal(address) \ 319 | (__extension__({ \ 320 | __asm__ __volatile__ \ 321 | ( \ 322 | "sts %0, %1\n\t" \ 323 | "spm\n\t" \ 324 | : \ 325 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 326 | "r" ((uint8_t)__BOOT_PAGE_ERASE), \ 327 | "z" ((uint16_t)address) \ 328 | ); \ 329 | })) 330 | 331 | #define __boot_page_erase_alternate(address) \ 332 | (__extension__({ \ 333 | __asm__ __volatile__ \ 334 | ( \ 335 | "sts %0, %1\n\t" \ 336 | "spm\n\t" \ 337 | ".word 0xffff\n\t" \ 338 | "nop\n\t" \ 339 | : \ 340 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 341 | "r" ((uint8_t)__BOOT_PAGE_ERASE), \ 342 | "z" ((uint16_t)address) \ 343 | ); \ 344 | })) 345 | 346 | #define __boot_page_erase_extended(address) \ 347 | (__extension__({ \ 348 | __asm__ __volatile__ \ 349 | ( \ 350 | "movw r30, %A3\n\t" \ 351 | "sts %1, %C3\n\t" \ 352 | "sts %0, %2\n\t" \ 353 | "spm\n\t" \ 354 | : \ 355 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 356 | "i" (_SFR_MEM_ADDR(RAMPZ)), \ 357 | "r" ((uint8_t)__BOOT_PAGE_ERASE), \ 358 | "r" ((uint32_t)address) \ 359 | : "r30", "r31" \ 360 | ); \ 361 | })) 362 | #define __boot_page_erase_extended_short(address) \ 363 | (__extension__({ \ 364 | __asm__ __volatile__ \ 365 | ( \ 366 | "movw r30, %A3\n\t" \ 367 | "out %1, %C3\n\t" \ 368 | "out %0, %2\n\t" \ 369 | "spm\n\t" \ 370 | : \ 371 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 372 | "i" (_SFR_IO_ADDR(RAMPZ)), \ 373 | "r" ((uint8_t)__BOOT_PAGE_ERASE), \ 374 | "r" ((uint32_t)address) \ 375 | : "r30", "r31" \ 376 | ); \ 377 | })) 378 | 379 | #define __boot_page_write_short(address) \ 380 | (__extension__({ \ 381 | __asm__ __volatile__ \ 382 | ( \ 383 | "out %0, %1\n\t" \ 384 | "spm\n\t" \ 385 | : \ 386 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 387 | "r" ((uint8_t)__BOOT_PAGE_WRITE), \ 388 | "z" ((uint16_t)address) \ 389 | ); \ 390 | })) 391 | 392 | #define __boot_page_write_normal(address) \ 393 | (__extension__({ \ 394 | __asm__ __volatile__ \ 395 | ( \ 396 | "sts %0, %1\n\t" \ 397 | "spm\n\t" \ 398 | : \ 399 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 400 | "r" ((uint8_t)__BOOT_PAGE_WRITE), \ 401 | "z" ((uint16_t)address) \ 402 | ); \ 403 | })) 404 | 405 | #define __boot_page_write_alternate(address) \ 406 | (__extension__({ \ 407 | __asm__ __volatile__ \ 408 | ( \ 409 | "sts %0, %1\n\t" \ 410 | "spm\n\t" \ 411 | ".word 0xffff\n\t" \ 412 | "nop\n\t" \ 413 | : \ 414 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 415 | "r" ((uint8_t)__BOOT_PAGE_WRITE), \ 416 | "z" ((uint16_t)address) \ 417 | ); \ 418 | })) 419 | 420 | #define __boot_page_write_extended(address) \ 421 | (__extension__({ \ 422 | __asm__ __volatile__ \ 423 | ( \ 424 | "movw r30, %A3\n\t" \ 425 | "sts %1, %C3\n\t" \ 426 | "sts %0, %2\n\t" \ 427 | "spm\n\t" \ 428 | : \ 429 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 430 | "i" (_SFR_MEM_ADDR(RAMPZ)), \ 431 | "r" ((uint8_t)__BOOT_PAGE_WRITE), \ 432 | "r" ((uint32_t)address) \ 433 | : "r30", "r31" \ 434 | ); \ 435 | })) 436 | #define __boot_page_write_extended_short(address) \ 437 | (__extension__({ \ 438 | __asm__ __volatile__ \ 439 | ( \ 440 | "movw r30, %A3\n\t" \ 441 | "out %1, %C3\n\t" \ 442 | "out %0, %2\n\t" \ 443 | "spm\n\t" \ 444 | : \ 445 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 446 | "i" (_SFR_IO_ADDR(RAMPZ)), \ 447 | "r" ((uint8_t)__BOOT_PAGE_WRITE), \ 448 | "r" ((uint32_t)address) \ 449 | : "r30", "r31" \ 450 | ); \ 451 | })) 452 | 453 | #define __boot_rww_enable_short() \ 454 | (__extension__({ \ 455 | __asm__ __volatile__ \ 456 | ( \ 457 | "out %0, %1\n\t" \ 458 | "spm\n\t" \ 459 | : \ 460 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 461 | "r" ((uint8_t)__BOOT_RWW_ENABLE) \ 462 | ); \ 463 | })) 464 | 465 | #define __boot_rww_enable() \ 466 | (__extension__({ \ 467 | __asm__ __volatile__ \ 468 | ( \ 469 | "sts %0, %1\n\t" \ 470 | "spm\n\t" \ 471 | : \ 472 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 473 | "r" ((uint8_t)__BOOT_RWW_ENABLE) \ 474 | ); \ 475 | })) 476 | 477 | #define __boot_rww_enable_alternate() \ 478 | (__extension__({ \ 479 | __asm__ __volatile__ \ 480 | ( \ 481 | "sts %0, %1\n\t" \ 482 | "spm\n\t" \ 483 | ".word 0xffff\n\t" \ 484 | "nop\n\t" \ 485 | : \ 486 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 487 | "r" ((uint8_t)__BOOT_RWW_ENABLE) \ 488 | ); \ 489 | })) 490 | 491 | /* From the mega16/mega128 data sheets (maybe others): 492 | 493 | Bits by SPM To set the Boot Loader Lock bits, write the desired data to 494 | R0, write "X0001001" to SPMCR and execute SPM within four clock cycles 495 | after writing SPMCR. The only accessible Lock bits are the Boot Lock bits 496 | that may prevent the Application and Boot Loader section from any 497 | software update by the MCU. 498 | 499 | If bits 5..2 in R0 are cleared (zero), the corresponding Boot Lock bit 500 | will be programmed if an SPM instruction is executed within four cycles 501 | after BLBSET and SPMEN (or SELFPRGEN) are set in SPMCR. The Z-pointer is 502 | don't care during this operation, but for future compatibility it is 503 | recommended to load the Z-pointer with $0001 (same as used for reading the 504 | Lock bits). For future compatibility It is also recommended to set bits 7, 505 | 6, 1, and 0 in R0 to 1 when writing the Lock bits. When programming the 506 | Lock bits the entire Flash can be read during the operation. */ 507 | 508 | #define __boot_lock_bits_set_short(lock_bits) \ 509 | (__extension__({ \ 510 | uint8_t value = (uint8_t)(~(lock_bits)); \ 511 | __asm__ __volatile__ \ 512 | ( \ 513 | "ldi r30, 1\n\t" \ 514 | "ldi r31, 0\n\t" \ 515 | "mov r0, %2\n\t" \ 516 | "out %0, %1\n\t" \ 517 | "spm\n\t" \ 518 | : \ 519 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 520 | "r" ((uint8_t)__BOOT_LOCK_BITS_SET), \ 521 | "r" (value) \ 522 | : "r0", "r30", "r31" \ 523 | ); \ 524 | })) 525 | 526 | #define __boot_lock_bits_set(lock_bits) \ 527 | (__extension__({ \ 528 | uint8_t value = (uint8_t)(~(lock_bits)); \ 529 | __asm__ __volatile__ \ 530 | ( \ 531 | "ldi r30, 1\n\t" \ 532 | "ldi r31, 0\n\t" \ 533 | "mov r0, %2\n\t" \ 534 | "sts %0, %1\n\t" \ 535 | "spm\n\t" \ 536 | : \ 537 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 538 | "r" ((uint8_t)__BOOT_LOCK_BITS_SET), \ 539 | "r" (value) \ 540 | : "r0", "r30", "r31" \ 541 | ); \ 542 | })) 543 | 544 | #define __boot_lock_bits_set_alternate(lock_bits) \ 545 | (__extension__({ \ 546 | uint8_t value = (uint8_t)(~(lock_bits)); \ 547 | __asm__ __volatile__ \ 548 | ( \ 549 | "ldi r30, 1\n\t" \ 550 | "ldi r31, 0\n\t" \ 551 | "mov r0, %2\n\t" \ 552 | "sts %0, %1\n\t" \ 553 | "spm\n\t" \ 554 | ".word 0xffff\n\t" \ 555 | "nop\n\t" \ 556 | : \ 557 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 558 | "r" ((uint8_t)__BOOT_LOCK_BITS_SET), \ 559 | "r" (value) \ 560 | : "r0", "r30", "r31" \ 561 | ); \ 562 | })) 563 | 564 | /* 565 | Reading lock and fuse bits: 566 | 567 | Similarly to writing the lock bits above, set BLBSET and SPMEN (or 568 | SELFPRGEN) bits in __SPMREG, and then (within four clock cycles) issue an 569 | LPM instruction. 570 | 571 | Z address: contents: 572 | 0x0000 low fuse bits 573 | 0x0001 lock bits 574 | 0x0002 extended fuse bits 575 | 0x0003 high fuse bits 576 | 577 | Sounds confusing, doesn't it? 578 | 579 | Unlike the macros in pgmspace.h, no need to care for non-enhanced 580 | cores here as these old cores do not provide SPM support anyway. 581 | */ 582 | 583 | /** \ingroup avr_boot 584 | \def GET_LOW_FUSE_BITS 585 | address to read the low fuse bits, using boot_lock_fuse_bits_get 586 | */ 587 | #define GET_LOW_FUSE_BITS (0x0000) 588 | /** \ingroup avr_boot 589 | \def GET_LOCK_BITS 590 | address to read the lock bits, using boot_lock_fuse_bits_get 591 | */ 592 | #define GET_LOCK_BITS (0x0001) 593 | /** \ingroup avr_boot 594 | \def GET_EXTENDED_FUSE_BITS 595 | address to read the extended fuse bits, using boot_lock_fuse_bits_get 596 | */ 597 | #define GET_EXTENDED_FUSE_BITS (0x0002) 598 | /** \ingroup avr_boot 599 | \def GET_HIGH_FUSE_BITS 600 | address to read the high fuse bits, using boot_lock_fuse_bits_get 601 | */ 602 | #define GET_HIGH_FUSE_BITS (0x0003) 603 | 604 | /** \ingroup avr_boot 605 | \def boot_lock_fuse_bits_get(address) 606 | 607 | Read the lock or fuse bits at \c address. 608 | 609 | Parameter \c address can be any of GET_LOW_FUSE_BITS, 610 | GET_LOCK_BITS, GET_EXTENDED_FUSE_BITS, or GET_HIGH_FUSE_BITS. 611 | 612 | \note The lock and fuse bits returned are the physical values, 613 | i.e. a bit returned as 0 means the corresponding fuse or lock bit 614 | is programmed. 615 | */ 616 | #define boot_lock_fuse_bits_get_short(address) \ 617 | (__extension__({ \ 618 | uint8_t __result; \ 619 | __asm__ __volatile__ \ 620 | ( \ 621 | "ldi r30, %3\n\t" \ 622 | "ldi r31, 0\n\t" \ 623 | "out %1, %2\n\t" \ 624 | "lpm %0, Z\n\t" \ 625 | : "=r" (__result) \ 626 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 627 | "r" ((uint8_t)__BOOT_LOCK_BITS_SET), \ 628 | "M" (address) \ 629 | : "r0", "r30", "r31" \ 630 | ); \ 631 | __result; \ 632 | })) 633 | 634 | #define boot_lock_fuse_bits_get(address) \ 635 | (__extension__({ \ 636 | uint8_t __result; \ 637 | __asm__ __volatile__ \ 638 | ( \ 639 | "ldi r30, %3\n\t" \ 640 | "ldi r31, 0\n\t" \ 641 | "sts %1, %2\n\t" \ 642 | "lpm %0, Z\n\t" \ 643 | : "=r" (__result) \ 644 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 645 | "r" ((uint8_t)__BOOT_LOCK_BITS_SET), \ 646 | "M" (address) \ 647 | : "r0", "r30", "r31" \ 648 | ); \ 649 | __result; \ 650 | })) 651 | 652 | /** \ingroup avr_boot 653 | \def boot_signature_byte_get(address) 654 | 655 | Read the Signature Row byte at \c address. For some MCU types, 656 | this function can also retrieve the factory-stored oscillator 657 | calibration bytes. 658 | 659 | Parameter \c address can be 0-0x1f as documented by the datasheet. 660 | \note The values are MCU type dependent. 661 | */ 662 | 663 | #define __BOOT_SIGROW_READ (_BV(__SPM_ENABLE) | _BV(SIGRD)) 664 | 665 | #define boot_signature_byte_get_short(addr) \ 666 | (__extension__({ \ 667 | uint16_t __addr16 = (uint16_t)(addr); \ 668 | uint8_t __result; \ 669 | __asm__ __volatile__ \ 670 | ( \ 671 | "out %1, %2\n\t" \ 672 | "lpm %0, Z" "\n\t" \ 673 | : "=r" (__result) \ 674 | : "i" (_SFR_IO_ADDR(__SPM_REG)), \ 675 | "r" ((uint8_t) __BOOT_SIGROW_READ), \ 676 | "z" (__addr16) \ 677 | ); \ 678 | __result; \ 679 | })) 680 | 681 | #define boot_signature_byte_get(addr) \ 682 | (__extension__({ \ 683 | uint16_t __addr16 = (uint16_t)(addr); \ 684 | uint8_t __result; \ 685 | __asm__ __volatile__ \ 686 | ( \ 687 | "sts %1, %2\n\t" \ 688 | "lpm %0, Z" "\n\t" \ 689 | : "=r" (__result) \ 690 | : "i" (_SFR_MEM_ADDR(__SPM_REG)), \ 691 | "r" ((uint8_t) __BOOT_SIGROW_READ), \ 692 | "z" (__addr16) \ 693 | ); \ 694 | __result; \ 695 | })) 696 | 697 | /** \ingroup avr_boot 698 | \def boot_page_fill(address, data) 699 | 700 | Fill the bootloader temporary page buffer for flash 701 | address with data word. 702 | 703 | \note The address is a byte address. The data is a word. The AVR 704 | writes data to the buffer a word at a time, but addresses the buffer 705 | per byte! So, increment your address by 2 between calls, and send 2 706 | data bytes in a word format! The LSB of the data is written to the lower 707 | address; the MSB of the data is written to the higher address.*/ 708 | 709 | /** \ingroup avr_boot 710 | \def boot_page_erase(address) 711 | 712 | Erase the flash page that contains address. 713 | 714 | \note address is a byte address in flash, not a word address. */ 715 | 716 | /** \ingroup avr_boot 717 | \def boot_page_write(address) 718 | 719 | Write the bootloader temporary page buffer 720 | to flash page that contains address. 721 | 722 | \note address is a byte address in flash, not a word address. */ 723 | 724 | /** \ingroup avr_boot 725 | \def boot_rww_enable() 726 | 727 | Enable the Read-While-Write memory section. */ 728 | 729 | /** \ingroup avr_boot 730 | \def boot_lock_bits_set(lock_bits) 731 | 732 | Set the bootloader lock bits. 733 | 734 | \param lock_bits A mask of which Boot Loader Lock Bits to set. 735 | 736 | \note In this context, a 'set bit' will be written to a zero value. 737 | Note also that only BLBxx bits can be programmed by this command. 738 | 739 | For example, to disallow the SPM instruction from writing to the Boot 740 | Loader memory section of flash, you would use this macro as such: 741 | 742 | \code 743 | boot_lock_bits_set (_BV (BLB11)); 744 | \endcode 745 | 746 | \note Like any lock bits, the Boot Loader Lock Bits, once set, 747 | cannot be cleared again except by a chip erase which will in turn 748 | also erase the boot loader itself. */ 749 | 750 | /* Normal versions of the macros use 16-bit addresses. 751 | Extended versions of the macros use 32-bit addresses. 752 | Alternate versions of the macros use 16-bit addresses and require special 753 | instruction sequences after LPM. 754 | 755 | FLASHEND is defined in the ioXXXX.h file. 756 | USHRT_MAX is defined in . */ 757 | 758 | #if defined(__AVR_ATmega161__) || defined(__AVR_ATmega163__) \ 759 | || defined(__AVR_ATmega323__) 760 | 761 | /* Alternate: ATmega161/163/323 and 16 bit address */ 762 | #define boot_page_fill(address, data) __boot_page_fill_alternate(address, data) 763 | #define boot_page_erase(address) __boot_page_erase_alternate(address) 764 | #define boot_page_write(address) __boot_page_write_alternate(address) 765 | #define boot_rww_enable() __boot_rww_enable_alternate() 766 | #define boot_lock_bits_set(lock_bits) __boot_lock_bits_set_alternate(lock_bits) 767 | 768 | #elif (FLASHEND > USHRT_MAX) 769 | 770 | /* Extended: >16 bit address */ 771 | #define boot_page_fill(address, data) __boot_page_fill_extended_short(address, data) 772 | #define boot_page_erase(address) __boot_page_erase_extended_short(address) 773 | #define boot_page_write(address) __boot_page_write_extended_short(address) 774 | #define boot_rww_enable() __boot_rww_enable_short() 775 | #define boot_lock_bits_set(lock_bits) __boot_lock_bits_set_short(lock_bits) 776 | 777 | #else 778 | 779 | /* Normal: 16 bit address */ 780 | #define boot_page_fill(address, data) __boot_page_fill_short(address, data) 781 | #define boot_page_erase(address) __boot_page_erase_short(address) 782 | #define boot_page_write(address) __boot_page_write_short(address) 783 | #define boot_rww_enable() __boot_rww_enable_short() 784 | #define boot_lock_bits_set(lock_bits) __boot_lock_bits_set_short(lock_bits) 785 | 786 | #endif 787 | 788 | /** \ingroup avr_boot 789 | 790 | Same as boot_page_fill() except it waits for eeprom and spm operations to 791 | complete before filling the page. */ 792 | 793 | #define boot_page_fill_safe(address, data) \ 794 | do { \ 795 | boot_spm_busy_wait(); \ 796 | eeprom_busy_wait(); \ 797 | boot_page_fill(address, data); \ 798 | } while (0) 799 | 800 | /** \ingroup avr_boot 801 | 802 | Same as boot_page_erase() except it waits for eeprom and spm operations to 803 | complete before erasing the page. */ 804 | 805 | #define boot_page_erase_safe(address) \ 806 | do { \ 807 | boot_spm_busy_wait(); \ 808 | eeprom_busy_wait(); \ 809 | boot_page_erase (address); \ 810 | } while (0) 811 | 812 | /** \ingroup avr_boot 813 | 814 | Same as boot_page_write() except it waits for eeprom and spm operations to 815 | complete before writing the page. */ 816 | 817 | #define boot_page_write_safe(address) \ 818 | do { \ 819 | boot_spm_busy_wait(); \ 820 | eeprom_busy_wait(); \ 821 | boot_page_write (address); \ 822 | } while (0) 823 | 824 | /** \ingroup avr_boot 825 | 826 | Same as boot_rww_enable() except waits for eeprom and spm operations to 827 | complete before enabling the RWW mameory. */ 828 | 829 | #define boot_rww_enable_safe() \ 830 | do { \ 831 | boot_spm_busy_wait(); \ 832 | eeprom_busy_wait(); \ 833 | boot_rww_enable(); \ 834 | } while (0) 835 | 836 | /** \ingroup avr_boot 837 | 838 | Same as boot_lock_bits_set() except waits for eeprom and spm operations to 839 | complete before setting the lock bits. */ 840 | 841 | #define boot_lock_bits_set_safe(lock_bits) \ 842 | do { \ 843 | boot_spm_busy_wait(); \ 844 | eeprom_busy_wait(); \ 845 | boot_lock_bits_set (lock_bits); \ 846 | } while (0) 847 | 848 | #endif /* _AVR_BOOT_H_ */ 849 | -------------------------------------------------------------------------------- /optiboot.c: -------------------------------------------------------------------------------- 1 | ////////////////////////////////////////////////////////////////////////// 2 | // 3 | // DualOptiboot 4 | // Optiboot based custom bootloader for Moteino 5 | // Enables wireless programming of Moteino wireless arduino clone 6 | // Copyright Felix Rusu (2013), felix@lowpowerlab.com 7 | // http://lowpowerlab.com/Moteino 8 | // 9 | ////////////////////////////////////////////////////////////////////////// 10 | // 11 | // This program is free software; you can redistribute it 12 | // and/or modify it under the terms of the GNU General 13 | // Public License as published by the Free Software 14 | // Foundation; either version 2 of the License, or 15 | // (at your option) any later version. 16 | // 17 | // This program is distributed in the hope that it will 18 | // be useful, but WITHOUT ANY WARRANTY; without even the 19 | // implied warranty of MERCHANTABILITY or FITNESS FOR A 20 | // PARTICULAR PURPOSE. See the GNU General Public 21 | // License for more details. 22 | // 23 | // You should have received a copy of the GNU General 24 | // Public License along with this program; if not, write 25 | // to the Free Software Foundation, Inc., 26 | // 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 27 | // 28 | // Licence can be viewed at 29 | // http://www.fsf.org/licenses/gpl.txt 30 | // 31 | // Please maintain this license information along with authorship 32 | // and copyright notices in any redistribution of this code 33 | // 34 | ////////////////////////////////////////////////////////////////////////// 35 | // 36 | // This Optiboot version is modified to add the capability of reflashing 37 | // from an external SPI flash memory chip. As configured this will work 38 | // with Moteino (www.lowpowerlab.com/Moteino) provided a SPI flash chip 39 | // is present on the dedicated onboard footprint. 40 | // Summary of how this Optiboot version works: 41 | // - it looks for an external flash chip 42 | // - if one is found (SPI returns valid data) it will further look 43 | // for a new sketch flash image signature and size 44 | // starting at address 0: FLXIMG:NN:XXXXXXXXXXX 45 | // where: - 'FLXIMG' is fixed signature indicating FLASH chip 46 | // contains a valid new flash image to be burned 47 | // - 'NN' are 2 size bytes (uint_16) indicating how long the 48 | // new flash image is (how many bytes to read), max 65536Bytes 49 | // - 'XXXXXX' are the de-hexified bytes of the flash 50 | // pages to be burned 51 | // - ':' colons have fixed positions (delimiters) 52 | // - if no valid signature/size are found, it will skip and 53 | // function as it normally would (listen to STK500 protocol on serial port) 54 | // 55 | // The added code will result in a compiled size of just under 1kb 56 | // (Originally Optiboot takes just under 0.5kb) 57 | // - Examples at: http://lowpowerlab.com/blog/category/moteino/wireless-programming/ 58 | // - Tested on atmega328P and atmega644/1284P 59 | // - Limited to 31K sketches for atmega328p and 64K sketches for atmega1284P. 60 | ////////////////////////////////////////////////////////////////////////// 61 | /**********************************************************/ 62 | /* Optiboot bootloader for Arduino */ 63 | /* */ 64 | /* http://optiboot.googlecode.com */ 65 | /* */ 66 | /* Arduino-maintained version : See README.TXT */ 67 | /* http://code.google.com/p/arduino/ */ 68 | /* It is the intent that changes not relevant to the */ 69 | /* Arduino production envionment get moved from the */ 70 | /* optiboot project to the arduino project in "lumps." */ 71 | /* */ 72 | /* Heavily optimised bootloader that is faster and */ 73 | /* smaller than the Arduino standard bootloader */ 74 | /* */ 75 | /* Enhancements: */ 76 | /* Fits in 512 bytes, saving 1.5K of code space */ 77 | /* Background page erasing speeds up programming */ 78 | /* Higher baud rate speeds up programming */ 79 | /* Written almost entirely in C */ 80 | /* Customisable timeout with accurate timeconstant */ 81 | /* Optional virtual UART. No hardware UART required. */ 82 | /* Optional virtual boot partition for devices without. */ 83 | /* */ 84 | /* What you lose: */ 85 | /* Implements a skeleton STK500 protocol which is */ 86 | /* missing several features including EEPROM */ 87 | /* programming and non-page-aligned writes */ 88 | /* High baud rate breaks compatibility with standard */ 89 | /* Arduino flash settings */ 90 | /* */ 91 | /* Fully supported: */ 92 | /* ATmega168 based devices (Diecimila etc) */ 93 | /* ATmega328P based devices (Duemilanove etc) */ 94 | /* */ 95 | /* Beta test (believed working.) */ 96 | /* ATmega8 based devices (Arduino legacy) */ 97 | /* ATmega328 non-picopower devices */ 98 | /* ATmega644P based devices (Sanguino) */ 99 | /* ATmega1284P based devices */ 100 | /* ATmega1280 based devices (Arduino Mega) */ 101 | /* */ 102 | /* Alpha test */ 103 | /* ATmega32 */ 104 | /* */ 105 | /* Work in progress: */ 106 | /* ATtiny84 based devices (Luminet) */ 107 | /* */ 108 | /* Does not support: */ 109 | /* USB based devices (eg. Teensy, Leonardo) */ 110 | /* */ 111 | /* Assumptions: */ 112 | /* The code makes several assumptions that reduce the */ 113 | /* code size. They are all true after a hardware reset, */ 114 | /* but may not be true if the bootloader is called by */ 115 | /* other means or on other hardware. */ 116 | /* No interrupts can occur */ 117 | /* UART and Timer 1 are set to their reset state */ 118 | /* SP points to RAMEND */ 119 | /* */ 120 | /* Code builds on code, libraries and optimisations from: */ 121 | /* stk500boot.c by Jason P. Kyle */ 122 | /* Arduino bootloader http://arduino.cc */ 123 | /* Spiff's 1K bootloader http://spiffie.org/know/arduino_1k_bootloader/bootloader.shtml */ 124 | /* avr-libc project http://nongnu.org/avr-libc */ 125 | /* Adaboot http://www.ladyada.net/library/arduino/bootloader.html */ 126 | /* AVR305 Atmel Application Note */ 127 | /* */ 128 | /* This program is free software; you can redistribute it */ 129 | /* and/or modify it under the terms of the GNU General */ 130 | /* Public License as published by the Free Software */ 131 | /* Foundation; either version 2 of the License, or */ 132 | /* (at your option) any later version. */ 133 | /* */ 134 | /* This program is distributed in the hope that it will */ 135 | /* be useful, but WITHOUT ANY WARRANTY; without even the */ 136 | /* implied warranty of MERCHANTABILITY or FITNESS FOR A */ 137 | /* PARTICULAR PURPOSE. See the GNU General Public */ 138 | /* License for more details. */ 139 | /* */ 140 | /* You should have received a copy of the GNU General */ 141 | /* Public License along with this program; if not, write */ 142 | /* to the Free Software Foundation, Inc., */ 143 | /* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ 144 | /* */ 145 | /* Licence can be viewed at */ 146 | /* http://www.fsf.org/licenses/gpl.txt */ 147 | /* */ 148 | /**********************************************************/ 149 | 150 | 151 | /**********************************************************/ 152 | /* */ 153 | /* Optional defines: */ 154 | /* */ 155 | /**********************************************************/ 156 | /* */ 157 | /* BIG_BOOT: */ 158 | /* Build a 1k bootloader, not 512 bytes. This turns on */ 159 | /* extra functionality. */ 160 | /* */ 161 | /* BAUD_RATE: */ 162 | /* Set bootloader baud rate. */ 163 | /* */ 164 | /* LUDICROUS_SPEED: */ 165 | /* 230400 baud :-) */ 166 | /* */ 167 | /* SOFT_UART: */ 168 | /* Use AVR305 soft-UART instead of hardware UART. */ 169 | /* */ 170 | /* LED_START_FLASHES: */ 171 | /* Number of LED flashes on bootup. */ 172 | /* */ 173 | /* LED_DATA_FLASH: */ 174 | /* Flash LED when transferring data. For boards without */ 175 | /* TX or RX LEDs, or for people who like blinky lights. */ 176 | /* */ 177 | /* SUPPORT_EEPROM: */ 178 | /* Support reading and writing from EEPROM. This is not */ 179 | /* used by Arduino, so off by default. */ 180 | /* */ 181 | /* TIMEOUT_MS: */ 182 | /* Bootloader timeout period, in milliseconds. */ 183 | /* 500,1000,2000,4000,8000 supported. */ 184 | /* */ 185 | /* UART: */ 186 | /* UART number (0..n) for devices with more than */ 187 | /* one hardware uart (644P, 1284P, etc) */ 188 | /* */ 189 | /**********************************************************/ 190 | 191 | /**********************************************************/ 192 | /* Version Numbers! */ 193 | /* */ 194 | /* Arduino Optiboot now includes this Version number in */ 195 | /* the source and object code. */ 196 | /* */ 197 | /* Version 3 was released as zip from the optiboot */ 198 | /* repository and was distributed with Arduino 0022. */ 199 | /* Version 4 starts with the arduino repository commit */ 200 | /* that brought the arduino repository up-to-date with */ 201 | /* the optiboot source tree changes since v3. */ 202 | /* Version 5 was created at the time of the new Makefile */ 203 | /* structure (Mar, 2013), even though no binaries changed*/ 204 | /* It would be good if versions implemented outside the */ 205 | /* official repository used an out-of-seqeunce version */ 206 | /* number (like 104.6 if based on based on 4.5) to */ 207 | /* prevent collisions. */ 208 | /* */ 209 | /**********************************************************/ 210 | 211 | /**********************************************************/ 212 | /* Edit History: */ 213 | /* */ 214 | /* Mar 2013 */ 215 | /* 5.0 WestfW: Major Makefile restructuring. */ 216 | /* See Makefile and pin_defs.h */ 217 | /* (no binary changes) */ 218 | /* */ 219 | /* 4.6 WestfW/Pito: Add ATmega32 support */ 220 | /* 4.6 WestfW/radoni: Don't set LED_PIN as an output if */ 221 | /* not used. (LED_START_FLASHES = 0) */ 222 | /* Jan 2013 */ 223 | /* 4.6 WestfW/dkinzer: use autoincrement lpm for read */ 224 | /* 4.6 WestfW/dkinzer: pass reset cause to app in R2 */ 225 | /* Mar 2012 */ 226 | /* 4.5 WestfW: add infrastructure for non-zero UARTS. */ 227 | /* 4.5 WestfW: fix SIGNATURE_2 for m644 (bad in avr-libc) */ 228 | /* Jan 2012: */ 229 | /* 4.5 WestfW: fix NRWW value for m1284. */ 230 | /* 4.4 WestfW: use attribute OS_main instead of naked for */ 231 | /* main(). This allows optimizations that we */ 232 | /* count on, which are prohibited in naked */ 233 | /* functions due to PR42240. (keeps us less */ 234 | /* than 512 bytes when compiler is gcc4.5 */ 235 | /* (code from 4.3.2 remains the same.) */ 236 | /* 4.4 WestfW and Maniacbug: Add m1284 support. This */ 237 | /* does not change the 328 binary, so the */ 238 | /* version number didn't change either. (?) */ 239 | /* June 2011: */ 240 | /* 4.4 WestfW: remove automatic soft_uart detect (didn't */ 241 | /* know what it was doing or why.) Added a */ 242 | /* check of the calculated BRG value instead. */ 243 | /* Version stays 4.4; existing binaries are */ 244 | /* not changed. */ 245 | /* 4.4 WestfW: add initialization of address to keep */ 246 | /* the compiler happy. Change SC'ed targets. */ 247 | /* Return the SW version via READ PARAM */ 248 | /* 4.3 WestfW: catch framing errors in getch(), so that */ 249 | /* AVRISP works without HW kludges. */ 250 | /* http://code.google.com/p/arduino/issues/detail?id=368n*/ 251 | /* 4.2 WestfW: reduce code size, fix timeouts, change */ 252 | /* verifySpace to use WDT instead of appstart */ 253 | /* 4.1 WestfW: put version number in binary. */ 254 | /**********************************************************/ 255 | 256 | #define LED_DATA_FLASH 1 257 | #define OPTIBOOT_MAJVER 5 258 | #define OPTIBOOT_MINVER 0 259 | 260 | #define MAKESTR(a) #a 261 | #define MAKEVER(a, b) MAKESTR(a*256+b) 262 | 263 | asm(" .section .version\n" 264 | "optiboot_version: .word " MAKEVER(OPTIBOOT_MAJVER, OPTIBOOT_MINVER) "\n" 265 | " .section .text\n"); 266 | 267 | #include 268 | #include 269 | #include 270 | 271 | // uses sts instructions, but this version uses out instructions 272 | // This saves cycles and program memory. 273 | #include "boot.h" 274 | 275 | 276 | // We don't use as those routines have interrupt overhead we don't need. 277 | 278 | #include "pin_defs.h" 279 | #include "stk500.h" 280 | 281 | #ifndef LED_START_FLASHES 282 | #define LED_START_FLASHES 1 283 | #endif 284 | 285 | #ifdef LUDICROUS_SPEED 286 | #define BAUD_RATE 230400L 287 | #endif 288 | 289 | /* set the UART baud rate defaults */ 290 | #ifndef BAUD_RATE 291 | #if F_CPU >= 8000000L 292 | #define BAUD_RATE 115200L // Highest rate Avrdude win32 will support 293 | #elsif F_CPU >= 1000000L 294 | #define BAUD_RATE 9600L // 19200 also supported, but with significant error 295 | #elsif F_CPU >= 128000L 296 | #define BAUD_RATE 4800L // Good for 128kHz internal RC 297 | #else 298 | #define BAUD_RATE 1200L // Good even at 32768Hz 299 | #endif 300 | #endif 301 | 302 | #ifndef UART 303 | #define UART 0 304 | #endif 305 | 306 | #define BAUD_SETTING (( (F_CPU + BAUD_RATE * 4L) / ((BAUD_RATE * 8L))) - 1 ) 307 | #define BAUD_ACTUAL (F_CPU/(8 * ((BAUD_SETTING)+1))) 308 | #define BAUD_ERROR (( 100*(BAUD_RATE - BAUD_ACTUAL) ) / BAUD_RATE) 309 | 310 | #if BAUD_ERROR >= 5 311 | #error BAUD_RATE error greater than 5% 312 | #elif BAUD_ERROR <= -5 313 | #error BAUD_RATE error greater than -5% 314 | #elif BAUD_ERROR >= 2 315 | #warning BAUD_RATE error greater than 2% 316 | #elif BAUD_ERROR <= -2 317 | #warning BAUD_RATE error greater than -2% 318 | #endif 319 | 320 | #if 0 321 | /* Switch in soft UART for hard baud rates */ 322 | /* 323 | * I don't understand what this was supposed to accomplish, where the 324 | * constant "280" came from, or why automatically (and perhaps unexpectedly) 325 | * switching to a soft uart is a good thing, so I'm undoing this in favor 326 | * of a range check using the same calc used to config the BRG... 327 | */ 328 | #if (F_CPU/BAUD_RATE) > 280 // > 57600 for 16MHz 329 | #ifndef SOFT_UART 330 | #define SOFT_UART 331 | #endif 332 | #endif 333 | #else // 0 334 | #if (F_CPU + BAUD_RATE * 4L) / (BAUD_RATE * 8L) - 1 > 250 335 | #error Unachievable baud rate (too slow) BAUD_RATE 336 | #endif // baud rate slow check 337 | #if (F_CPU + BAUD_RATE * 4L) / (BAUD_RATE * 8L) - 1 < 3 338 | #error Unachievable baud rate (too fast) BAUD_RATE 339 | #endif // baud rate fastn check 340 | #endif 341 | 342 | /* Watchdog settings */ 343 | #define WATCHDOG_OFF (0) 344 | #define WATCHDOG_16MS (_BV(WDE)) 345 | #define WATCHDOG_32MS (_BV(WDP0) | _BV(WDE)) 346 | #define WATCHDOG_64MS (_BV(WDP1) | _BV(WDE)) 347 | #define WATCHDOG_125MS (_BV(WDP1) | _BV(WDP0) | _BV(WDE)) 348 | #define WATCHDOG_250MS (_BV(WDP2) | _BV(WDE)) 349 | #define WATCHDOG_500MS (_BV(WDP2) | _BV(WDP0) | _BV(WDE)) 350 | #define WATCHDOG_1S (_BV(WDP2) | _BV(WDP1) | _BV(WDE)) 351 | #define WATCHDOG_2S (_BV(WDP2) | _BV(WDP1) | _BV(WDP0) | _BV(WDE)) 352 | #ifndef __AVR_ATmega8__ 353 | #define WATCHDOG_4S (_BV(WDP3) | _BV(WDE)) 354 | #define WATCHDOG_8S (_BV(WDP3) | _BV(WDP0) | _BV(WDE)) 355 | #endif 356 | 357 | /* Function Prototypes */ 358 | /* The main function is in init9, which removes the interrupt vector table */ 359 | /* we don't need. It is also 'naked', which means the compiler does not */ 360 | /* generate any entry or exit code itself. */ 361 | int main(void) __attribute__ ((OS_main)) __attribute__ ((section (".init9"))); 362 | void putch(char); 363 | uint8_t getch(void); 364 | static inline void getNch(uint8_t); /* "static inline" is a compiler hint to reduce code size */ 365 | void verifySpace(); 366 | static inline void flash_led(uint8_t); 367 | uint8_t getLen(); 368 | static inline void watchdogReset(); 369 | void watchdogConfig(uint8_t x); 370 | #ifdef SOFT_UART 371 | void uartDelay() __attribute__ ((naked)); 372 | #endif 373 | void appStart(uint8_t rstFlags) __attribute__ ((naked)); 374 | 375 | /* 376 | * NRWW memory 377 | * Addresses below NRWW (Non-Read-While-Write) can be programmed while 378 | * continuing to run code from flash, slightly speeding up programming 379 | * time. Beware that Atmel data sheets specify this as a WORD address, 380 | * while optiboot will be comparing against a 16-bit byte address. This 381 | * means that on a part with 128kB of memory, the upper part of the lower 382 | * 64k will get NRWW processing as well, even though it doesn't need it. 383 | * That's OK. In fact, you can disable the overlapping processing for 384 | * a part entirely by setting NRWWSTART to zero. This reduces code 385 | * space a bit, at the expense of being slightly slower, overall. 386 | * 387 | * RAMSTART should be self-explanatory. It's bigger on parts with a 388 | * lot of peripheral registers. 389 | */ 390 | #if defined(__AVR_ATmega168__) 391 | #define RAMSTART (0x100) 392 | #define NRWWSTART (0x3800) 393 | #elif defined(__AVR_ATmega328P__) || defined(__AVR_ATmega32__) 394 | #define RAMSTART (0x100) 395 | #define NRWWSTART (0x7000) 396 | #elif defined (__AVR_ATmega644P__) 397 | #define RAMSTART (0x100) 398 | #define NRWWSTART (0xE000) 399 | // correct for a bug in avr-libc 400 | #undef SIGNATURE_2 401 | #define SIGNATURE_2 0x0A 402 | #elif defined (__AVR_ATmega1284P__) 403 | #define RAMSTART (0x100) 404 | #define NRWWSTART (0xE000) 405 | #elif defined(__AVR_ATtiny84__) 406 | #define RAMSTART (0x100) 407 | #define NRWWSTART (0x0000) 408 | #elif defined(__AVR_ATmega1280__) 409 | #define RAMSTART (0x200) 410 | #define NRWWSTART (0xE000) 411 | #elif defined(__AVR_ATmega8__) || defined(__AVR_ATmega88__) 412 | #define RAMSTART (0x100) 413 | #define NRWWSTART (0x1800) 414 | #endif 415 | 416 | /* C zero initialises all global variables. However, that requires */ 417 | /* These definitions are NOT zero initialised, but that doesn't matter */ 418 | /* This allows us to drop the zero init code, saving us memory */ 419 | #define buff ((uint8_t*)(RAMSTART)) 420 | #ifdef VIRTUAL_BOOT_PARTITION 421 | #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) 422 | #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) 423 | #endif 424 | 425 | /* 426 | * Handle devices with up to 4 uarts (eg m1280.) Rather inelegantly. 427 | * Note that mega8/m32 still needs special handling, because ubrr is handled 428 | * differently. 429 | */ 430 | #if UART == 0 431 | # define UART_SRA UCSR0A 432 | # define UART_SRB UCSR0B 433 | # define UART_SRC UCSR0C 434 | # define UART_SRL UBRR0L 435 | # define UART_UDR UDR0 436 | #elif UART == 1 437 | #if !defined(UDR1) 438 | #error UART == 1, but no UART1 on device 439 | #endif 440 | # define UART_SRA UCSR1A 441 | # define UART_SRB UCSR1B 442 | # define UART_SRC UCSR1C 443 | # define UART_SRL UBRR1L 444 | # define UART_UDR UDR1 445 | #elif UART == 2 446 | #if !defined(UDR2) 447 | #error UART == 2, but no UART2 on device 448 | #endif 449 | # define UART_SRA UCSR2A 450 | # define UART_SRB UCSR2B 451 | # define UART_SRC UCSR2C 452 | # define UART_SRL UBRR2L 453 | # define UART_UDR UDR2 454 | #elif UART == 3 455 | #if !defined(UDR1) 456 | #error UART == 3, but no UART3 on device 457 | #endif 458 | # define UART_SRA UCSR3A 459 | # define UART_SRB UCSR3B 460 | # define UART_SRC UCSR3C 461 | # define UART_SRL UBRR3L 462 | # define UART_UDR UDR3 463 | #endif 464 | 465 | /******************* SPI FLASH Code **********************************/ 466 | // This code will handle the reading/erasing the external SPI FLASH memory 467 | // assumed to have the SPI_CS on D8 on Moteino (Atmega328P) 468 | #define SPI_MODE0 0x00 469 | #define SPI_MODE_MASK 0x0C // CPOL = bit 3, CPHA = bit 2 on SPCR 470 | #define SPI_CLOCK_MASK 0x03 // SPR1 = bit 1, SPR0 = bit 0 on SPCR 471 | #define SPI_2XCLOCK_MASK 0x01 // SPI2X = bit 0 on SPSR 472 | #define SPI_CLOCK_DIV2 0x04 473 | 474 | #if defined(__AVR_ATmega168__) || defined(__AVR_ATmega328P__) || defined(__AVR_ATmega88) || defined(__AVR_ATmega8__) || defined(__AVR_ATmega88__) 475 | #define FLASHSS_DDR DDRB 476 | #define FLASHSS_PORT PORTB 477 | #define FLASHSS PINB0 478 | #define SS PINB2 479 | #elif defined (__AVR_ATmega1284P__) || defined (__AVR_ATmega644P__) 480 | #define FLASHSS_DDR DDRC 481 | #define FLASHSS_PORT PORTC 482 | #define FLASHSS PINC7 483 | #define SS PINB4 484 | #endif 485 | 486 | #define FLASH_SELECT { FLASHSS_PORT &= ~(_BV(FLASHSS)); } 487 | #define FLASH_UNSELECT { FLASHSS_PORT |= _BV(FLASHSS); } 488 | 489 | #define SPIFLASH_STATUSWRITE 0x01 // write status register 490 | #define SPIFLASH_STATUSREAD 0x05 // read status register 491 | #define SPIFLASH_WRITEENABLE 0x06 // write enable 492 | #define SPIFLASH_ARRAYREADLOWFREQ 0x03 // read array (low frequency) 493 | #define SPIFLASH_BLOCKERASE_32K 0x52 // erase one 32K block of flash memory 494 | #define SPIFLASH_BLOCKERASE_64K 0xD8 // erase one 32K block of flash memory 495 | #define SPIFLASH_JEDECID 0x9F // read JEDEC ID 496 | //#define DEBUG_ON // uncomment to enable Serial debugging 497 | // (will output different characters depending on which path the bootloader takes) 498 | 499 | uint8_t SPI_transfer(uint8_t _data) { 500 | SPDR = _data; 501 | while (!(SPSR & _BV(SPIF))); 502 | return SPDR; 503 | } 504 | 505 | uint8_t FLASH_busy() 506 | { 507 | FLASH_SELECT; 508 | SPI_transfer(SPIFLASH_STATUSREAD); 509 | uint8_t status = SPI_transfer(0); 510 | FLASH_UNSELECT; 511 | return status & 1; 512 | } 513 | 514 | void FLASH_command(uint8_t cmd, uint8_t isWrite){ 515 | if (isWrite) 516 | { 517 | FLASH_command(SPIFLASH_WRITEENABLE, 0); // Write Enable 518 | FLASH_UNSELECT; 519 | } 520 | while(FLASH_busy()); //wait for chip to become available 521 | FLASH_SELECT; 522 | SPI_transfer(cmd); 523 | } 524 | 525 | uint8_t FLASH_readByte(uint32_t addr) { 526 | FLASH_command(SPIFLASH_ARRAYREADLOWFREQ, 0); 527 | SPI_transfer(addr >> 16); 528 | SPI_transfer(addr >> 8); 529 | SPI_transfer(addr); 530 | //SPI.transfer(0); //"dont care", needed with SPIFLASH_ARRAYREAD command only 531 | uint8_t result = SPI_transfer(0); 532 | FLASH_UNSELECT; 533 | return result; 534 | } 535 | 536 | void CheckFlashImage() { 537 | #ifdef DEBUG_ON 538 | putch('F'); 539 | #endif 540 | watchdogConfig(WATCHDOG_OFF); 541 | 542 | //SPI INIT 543 | #if defined(__AVR_ATmega168__) || defined(__AVR_ATmega328P__) || defined(__AVR_ATmega88) || defined(__AVR_ATmega8__) || defined(__AVR_ATmega88__) 544 | DDRB |= _BV(FLASHSS) | _BV(SS) | _BV(PB3) | _BV(PB5); //OUTPUTS for FLASH_SS and SS, MOSI, SCK 545 | FLASH_UNSELECT; //unselect FLASH chip 546 | PORTB |= _BV(SS); //set SS HIGH 547 | #elif defined (__AVR_ATmega1284P__) || defined (__AVR_ATmega644P__) 548 | DDRC |= _BV(FLASHSS); //OUTPUT for FLASH_SS 549 | DDRB |= _BV(SS) | _BV(PB5) | _BV(PB7); //OUTPUTS for SS, MOSI, SCK 550 | FLASH_UNSELECT; //unselect FLASH chip 551 | PORTB |= _BV(SS); //set SS HIGH 552 | #endif 553 | 554 | //SPCR &= ~(_BV(DORD)); //MSB first 555 | //SPCR = (SPCR & ~SPI_MODE_MASK) | SPI_MODE0 ; //SPI MODE 0 556 | //SPCR = (SPCR & ~SPI_CLOCK_MASK) | (SPI_CLOCK_DIV2 & SPI_CLOCK_MASK); //clock divider = 2 557 | //SPSR = (SPSR & ~SPI_2XCLOCK_MASK) | ((SPI_CLOCK_DIV2 >> 2) & SPI_2XCLOCK_MASK); 558 | 559 | // Warning: if the SS pin ever becomes a LOW INPUT then SPI automatically switches to Slave, so the data direction of the SS pin MUST be kept as OUTPUT. 560 | SPCR |= _BV(MSTR) | _BV(SPE); //enable SPI and set SPI to MASTER mode 561 | 562 | //read first byte of JEDECID, if chip is present it should return a non-0 and non-FF value 563 | FLASH_SELECT; 564 | SPI_transfer(SPIFLASH_JEDECID); 565 | uint8_t deviceId = SPI_transfer(0); 566 | FLASH_UNSELECT; 567 | if (deviceId==0 || deviceId==0xFF) return; 568 | 569 | //global unprotect 570 | FLASH_command(SPIFLASH_STATUSWRITE, 1); 571 | SPI_transfer(0); 572 | FLASH_UNSELECT; 573 | 574 | //check if any flash image exists on external FLASH chip 575 | if (FLASH_readByte(0)=='F' && FLASH_readByte(1)=='L' && FLASH_readByte(2)=='X' && FLASH_readByte(6)==':' && FLASH_readByte(9)==':') 576 | { 577 | #ifdef DEBUG_ON 578 | putch('L'); 579 | #endif 580 | 581 | uint16_t imagesize = (FLASH_readByte(7)<<8) | FLASH_readByte(8); 582 | if (imagesize%2!=0) return; //basic check that we got even # of bytes 583 | 584 | uint16_t b, i, nextAddress=0; 585 | 586 | LED_PIN |= _BV(LED); 587 | for (i=0; i 0 685 | // Set up Timer 1 for timeout counter 686 | TCCR1B = _BV(CS12) | _BV(CS10); // div 1024 687 | #endif 688 | #ifndef SOFT_UART 689 | #if defined(__AVR_ATmega8__) || defined (__AVR_ATmega32__) 690 | UCSRA = _BV(U2X); //Double speed mode USART 691 | UCSRB = _BV(RXEN) | _BV(TXEN); // enable Rx & Tx 692 | UCSRC = _BV(URSEL) | _BV(UCSZ1) | _BV(UCSZ0); // config USART; 8N1 693 | UBRRL = (uint8_t)( (F_CPU + BAUD_RATE * 4L) / (BAUD_RATE * 8L) - 1 ); 694 | #else 695 | UART_SRA = _BV(U2X0); //Double speed mode USART0 696 | UART_SRB = _BV(RXEN0) | _BV(TXEN0); 697 | UART_SRC = _BV(UCSZ00) | _BV(UCSZ01); 698 | UART_SRL = (uint8_t)( (F_CPU + BAUD_RATE * 4L) / (BAUD_RATE * 8L) - 1 ); 699 | #endif 700 | #endif 701 | 702 | // Set up watchdog to trigger after 500ms 703 | watchdogConfig(WATCHDOG_1S); 704 | 705 | #if (LED_START_FLASHES > 0) || defined(LED_DATA_FLASH) 706 | /* Set LED pin as output */ 707 | LED_DDR |= _BV(LED); 708 | #endif 709 | 710 | #ifdef SOFT_UART 711 | /* Set TX pin as output */ 712 | UART_DDR |= _BV(UART_TX_BIT); 713 | #endif 714 | 715 | #if LED_START_FLASHES > 0 716 | /* Flash onboard LED to signal entering of bootloader */ 717 | flash_led(LED_START_FLASHES * 2); 718 | #endif 719 | 720 | /* Forever loop */ 721 | for (;;) { 722 | /* get character from UART */ 723 | ch = getch(); 724 | 725 | if(ch == STK_GET_PARAMETER) { 726 | unsigned char which = getch(); 727 | verifySpace(); 728 | if (which == 0x82) { 729 | /* 730 | * Send optiboot version as "minor SW version" 731 | */ 732 | putch(OPTIBOOT_MINVER); 733 | } else if (which == 0x81) { 734 | putch(OPTIBOOT_MAJVER); 735 | } else { 736 | /* 737 | * GET PARAMETER returns a generic 0x03 reply for 738 | * other parameters - enough to keep Avrdude happy 739 | */ 740 | putch(0x03); 741 | } 742 | } 743 | else if(ch == STK_SET_DEVICE) { 744 | // SET DEVICE is ignored 745 | getNch(20); 746 | } 747 | else if(ch == STK_SET_DEVICE_EXT) { 748 | // SET DEVICE EXT is ignored 749 | getNch(5); 750 | } 751 | else if(ch == STK_LOAD_ADDRESS) { 752 | // LOAD ADDRESS 753 | uint16_t newAddress; 754 | newAddress = getch(); 755 | newAddress = (newAddress & 0xff) | (getch() << 8); 756 | #ifdef RAMPZ 757 | // Transfer top bit to RAMPZ 758 | RAMPZ = (newAddress & 0x8000) ? 1 : 0; 759 | #endif 760 | newAddress += newAddress; // Convert from word address to byte address 761 | address = newAddress; 762 | verifySpace(); 763 | } 764 | else if(ch == STK_UNIVERSAL) { 765 | // UNIVERSAL command is ignored 766 | getNch(4); 767 | putch(0x00); 768 | } 769 | /* Write memory, length is big endian and is in bytes */ 770 | else if(ch == STK_PROG_PAGE) { 771 | // PROGRAM PAGE - we support flash programming only, not EEPROM 772 | uint8_t *bufPtr; 773 | uint16_t addrPtr; 774 | 775 | getch(); /* getlen() */ 776 | length = getch(); 777 | getch(); 778 | 779 | // If we are in RWW section, immediately start page erase 780 | if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address); 781 | 782 | // While that is going on, read in page contents 783 | bufPtr = buff; 784 | do *bufPtr++ = getch(); 785 | while (--length); 786 | 787 | // If we are in NRWW section, page erase has to be delayed until now. 788 | // Todo: Take RAMPZ into account (not doing so just means that we will 789 | // treat the top of both "pages" of flash as NRWW, for a slight speed 790 | // decrease, so fixing this is not urgent.) 791 | if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address); 792 | 793 | // Read command terminator, start reply 794 | verifySpace(); 795 | 796 | // If only a partial page is to be programmed, the erase might not be complete. 797 | // So check that here 798 | boot_spm_busy_wait(); 799 | 800 | #ifdef VIRTUAL_BOOT_PARTITION 801 | if ((uint16_t)(void*)address == 0) { 802 | // This is the reset vector page. We need to live-patch the code so the 803 | // bootloader runs. 804 | // 805 | // Move RESET vector to WDT vector 806 | uint16_t vect = buff[0] | (buff[1]<<8); 807 | rstVect = vect; 808 | wdtVect = buff[8] | (buff[9]<<8); 809 | vect -= 4; // Instruction is a relative jump (rjmp), so recalculate. 810 | buff[8] = vect & 0xff; 811 | buff[9] = vect >> 8; 812 | 813 | // Add jump to bootloader at RESET vector 814 | buff[0] = 0x7f; 815 | buff[1] = 0xce; // rjmp 0x1d00 instruction 816 | } 817 | #endif 818 | 819 | // Copy buffer into programming buffer 820 | bufPtr = buff; 821 | addrPtr = (uint16_t)(void*)address; 822 | ch = SPM_PAGESIZE / 2; 823 | do { 824 | uint16_t a; 825 | a = *bufPtr++; 826 | a |= (*bufPtr++) << 8; 827 | __boot_page_fill_short((uint16_t)(void*)addrPtr,a); 828 | addrPtr += 2; 829 | } while (--ch); 830 | 831 | // Write from programming buffer 832 | __boot_page_write_short((uint16_t)(void*)address); 833 | boot_spm_busy_wait(); 834 | 835 | #if defined(RWWSRE) 836 | // Reenable read access to flash 837 | boot_rww_enable(); 838 | #endif 839 | 840 | } 841 | /* Read memory block mode, length is big endian. */ 842 | else if(ch == STK_READ_PAGE) { 843 | // READ PAGE - we only read flash 844 | getch(); /* getlen() */ 845 | length = getch(); 846 | getch(); 847 | 848 | verifySpace(); 849 | do { 850 | #ifdef VIRTUAL_BOOT_PARTITION 851 | // Undo vector patch in bottom page so verify passes 852 | if (address == 0) ch=rstVect & 0xff; 853 | else if (address == 1) ch=rstVect >> 8; 854 | else if (address == 8) ch=wdtVect & 0xff; 855 | else if (address == 9) ch=wdtVect >> 8; 856 | else ch = pgm_read_byte_near(address); 857 | address++; 858 | #elif defined(RAMPZ) 859 | // Since RAMPZ should already be set, we need to use EPLM directly. 860 | // Also, we can use the autoincrement version of lpm to update "address" 861 | // do putch(pgm_read_byte_near(address++)); 862 | // while (--length); 863 | // read a Flash and increment the address (may increment RAMPZ) 864 | __asm__ ("elpm %0,Z+\n" : "=r" (ch), "=z" (address): "1" (address)); 865 | #else 866 | // read a Flash byte and increment the address 867 | __asm__ ("lpm %0,Z+\n" : "=r" (ch), "=z" (address): "1" (address)); 868 | #endif 869 | putch(ch); 870 | } while (--length); 871 | } 872 | 873 | /* Get device signature bytes */ 874 | else if(ch == STK_READ_SIGN) { 875 | // READ SIGN - return what Avrdude wants to hear 876 | verifySpace(); 877 | putch(SIGNATURE_0); 878 | putch(SIGNATURE_1); 879 | putch(SIGNATURE_2); 880 | } 881 | else if (ch == STK_LEAVE_PROGMODE) { /* 'Q' */ 882 | // Adaboot no-wait mod 883 | watchdogConfig(WATCHDOG_16MS); 884 | verifySpace(); 885 | } 886 | else { 887 | // This covers the response to commands like STK_ENTER_PROGMODE 888 | verifySpace(); 889 | } 890 | putch(STK_OK); 891 | } 892 | } 893 | 894 | void putch(char ch) { 895 | #ifndef SOFT_UART 896 | while (!(UART_SRA & _BV(UDRE0))); 897 | UART_UDR = ch; 898 | #else 899 | __asm__ __volatile__ ( 900 | " com %[ch]\n" // ones complement, carry set 901 | " sec\n" 902 | "1: brcc 2f\n" 903 | " cbi %[uartPort],%[uartBit]\n" 904 | " rjmp 3f\n" 905 | "2: sbi %[uartPort],%[uartBit]\n" 906 | " nop\n" 907 | "3: rcall uartDelay\n" 908 | " rcall uartDelay\n" 909 | " lsr %[ch]\n" 910 | " dec %[bitcnt]\n" 911 | " brne 1b\n" 912 | : 913 | : 914 | [bitcnt] "d" (10), 915 | [ch] "r" (ch), 916 | [uartPort] "I" (_SFR_IO_ADDR(UART_PORT)), 917 | [uartBit] "I" (UART_TX_BIT) 918 | : 919 | "r25" 920 | ); 921 | #endif 922 | } 923 | 924 | uint8_t getch(void) { 925 | uint8_t ch; 926 | 927 | #ifdef LED_DATA_FLASH 928 | #if defined(__AVR_ATmega8__) || defined (__AVR_ATmega32__) 929 | LED_PORT ^= _BV(LED); 930 | #else 931 | LED_PIN |= _BV(LED); 932 | #endif 933 | #endif 934 | 935 | #ifdef SOFT_UART 936 | __asm__ __volatile__ ( 937 | "1: sbic %[uartPin],%[uartBit]\n" // Wait for start edge 938 | " rjmp 1b\n" 939 | " rcall uartDelay\n" // Get to middle of start bit 940 | "2: rcall uartDelay\n" // Wait 1 bit period 941 | " rcall uartDelay\n" // Wait 1 bit period 942 | " clc\n" 943 | " sbic %[uartPin],%[uartBit]\n" 944 | " sec\n" 945 | " dec %[bitCnt]\n" 946 | " breq 3f\n" 947 | " ror %[ch]\n" 948 | " rjmp 2b\n" 949 | "3:\n" 950 | : 951 | [ch] "=r" (ch) 952 | : 953 | [bitCnt] "d" (9), 954 | [uartPin] "I" (_SFR_IO_ADDR(UART_PIN)), 955 | [uartBit] "I" (UART_RX_BIT) 956 | : 957 | "r25" 958 | ); 959 | #else 960 | while(!(UART_SRA & _BV(RXC0))) 961 | ; 962 | if (!(UART_SRA & _BV(FE0))) { 963 | /* 964 | * A Framing Error indicates (probably) that something is talking 965 | * to us at the wrong bit rate. Assume that this is because it 966 | * expects to be talking to the application, and DON'T reset the 967 | * watchdog. This should cause the bootloader to abort and run 968 | * the application "soon", if it keeps happening. (Note that we 969 | * don't care that an invalid char is returned...) 970 | */ 971 | watchdogReset(); 972 | } 973 | 974 | ch = UART_UDR; 975 | #endif 976 | 977 | #ifdef LED_DATA_FLASH 978 | #if defined(__AVR_ATmega8__) || defined (__AVR_ATmega32__) 979 | LED_PORT ^= _BV(LED); 980 | #else 981 | LED_PIN |= _BV(LED); 982 | #endif 983 | #endif 984 | 985 | return ch; 986 | } 987 | 988 | #ifdef SOFT_UART 989 | // AVR305 equation: #define UART_B_VALUE (((F_CPU/BAUD_RATE)-23)/6) 990 | // Adding 3 to numerator simulates nearest rounding for more accurate baud rates 991 | #define UART_B_VALUE (((F_CPU/BAUD_RATE)-20)/6) 992 | #if UART_B_VALUE > 255 993 | #error Baud rate too slow for soft UART 994 | #endif 995 | 996 | void uartDelay() { 997 | __asm__ __volatile__ ( 998 | "ldi r25,%[count]\n" 999 | "1:dec r25\n" 1000 | "brne 1b\n" 1001 | "ret\n" 1002 | ::[count] "M" (UART_B_VALUE) 1003 | ); 1004 | } 1005 | #endif 1006 | 1007 | void getNch(uint8_t count) { 1008 | do getch(); while (--count); 1009 | verifySpace(); 1010 | } 1011 | 1012 | void verifySpace() { 1013 | if (getch() != CRC_EOP) { 1014 | watchdogConfig(WATCHDOG_16MS); // shorten WD timeout 1015 | while (1) // and busy-loop so that WD causes 1016 | ; // a reset and app start. 1017 | } 1018 | putch(STK_INSYNC); 1019 | } 1020 | 1021 | #if LED_START_FLASHES > 0 1022 | void flash_led(uint8_t count) { 1023 | do { 1024 | TCNT1 = -(F_CPU/(1024*16)); 1025 | TIFR1 = _BV(TOV1); 1026 | while(!(TIFR1 & _BV(TOV1))); 1027 | #if defined(__AVR_ATmega8__) || defined (__AVR_ATmega32__) 1028 | LED_PORT ^= _BV(LED); 1029 | #else 1030 | LED_PIN |= _BV(LED); 1031 | #endif 1032 | watchdogReset(); 1033 | } while (--count); 1034 | } 1035 | #endif 1036 | 1037 | // Watchdog functions. These are only safe with interrupts turned off. 1038 | void watchdogReset() { 1039 | __asm__ __volatile__ ( 1040 | "wdr\n" 1041 | ); 1042 | } 1043 | 1044 | void watchdogConfig(uint8_t x) { 1045 | WDTCSR = _BV(WDCE) | _BV(WDE); 1046 | WDTCSR = x; 1047 | } 1048 | 1049 | void appStart(uint8_t rstFlags) { 1050 | // save the reset flags in the designated register 1051 | // This can be saved in a main program by putting code in .init0 (which 1052 | // executes before normal c init code) to save R2 to a global variable. 1053 | __asm__ __volatile__ ("mov r2, %0\n" :: "r" (rstFlags)); 1054 | 1055 | watchdogConfig(WATCHDOG_OFF); 1056 | __asm__ __volatile__ ( 1057 | #ifdef VIRTUAL_BOOT_PARTITION 1058 | // Jump to WDT vector 1059 | "ldi r30,4\n" 1060 | "clr r31\n" 1061 | #else 1062 | // Jump to RST vector 1063 | "clr r30\n" 1064 | "clr r31\n" 1065 | #endif 1066 | "ijmp\n" 1067 | ); 1068 | } 1069 | -------------------------------------------------------------------------------- /pin_defs.h: -------------------------------------------------------------------------------- 1 | /*------------------------------------------------------------------------ */ 2 | #if defined(__AVR_ATmega168__) || defined(__AVR_ATmega328P__) || defined(__AVR_ATmega88) || defined(__AVR_ATmega8__) || defined(__AVR_ATmega88__) 3 | /*------------------------------------------------------------------------ */ 4 | 5 | /* Onboard LED is connected to pin PB5 in Arduino NG, Diecimila, and Duemilanove 6 | */ 7 | #if !defined(LED) 8 | #define LED B1 //D9 9 | #endif 10 | 11 | /* Ports for soft UART */ 12 | #ifdef SOFT_UART 13 | #define UART_PORT PORTD 14 | #define UART_PIN PIND 15 | #define UART_DDR DDRD 16 | #define UART_TX_BIT 1 17 | #define UART_RX_BIT 0 18 | #endif 19 | #endif 20 | 21 | #if defined(__AVR_ATmega8__) || defined(__AVR_ATmega32__) 22 | //Name conversion R.Wiersma 23 | #define UCSR0A UCSRA 24 | #define UDR0 UDR 25 | #define UDRE0 UDRE 26 | #define RXC0 RXC 27 | #define FE0 FE 28 | #define TIFR1 TIFR 29 | #define WDTCSR WDTCR 30 | #endif 31 | #if defined(__AVR_ATmega32__) 32 | #define WDCE WDTOE 33 | #endif 34 | 35 | /* Luminet support */ 36 | /*------------------------------------------------------------------------ */ 37 | #if defined(__AVR_ATtiny84__) 38 | /*------------------------------------------------------------------------ */ 39 | /* Red LED is connected to pin PA4 */ 40 | #if !defined(LED) 41 | #define LED A4 42 | #endif 43 | 44 | /* Ports for soft UART - left port only for now. TX/RX on PA2/PA3 */ 45 | #ifdef SOFT_UART 46 | #define UART_PORT PORTA 47 | #define UART_PIN PINA 48 | #define UART_DDR DDRA 49 | #define UART_TX_BIT 2 50 | #define UART_RX_BIT 3 51 | #endif 52 | #endif 53 | 54 | /*------------------------------------------------------------------------ */ 55 | /* Sanguino support (and other 40pin DIP cpus) */ 56 | #if defined(__AVR_ATmega644P__) || defined(__AVR_ATmega1284P__) || defined(__AVR_ATmega32__) 57 | /*------------------------------------------------------------------------ */ 58 | /* Onboard LED is connected to pin PB0 on Sanguino */ 59 | #if !defined(LED) 60 | #define LED D7 //Moteino MEGA D15 61 | #endif 62 | 63 | /* Ports for soft UART */ 64 | #ifdef SOFT_UART 65 | #define UART_PORT PORTD 66 | #define UART_PIN PIND 67 | #define UART_DDR DDRD 68 | #define UART_TX_BIT 1 69 | #define UART_RX_BIT 0 70 | #endif 71 | #endif 72 | 73 | /*------------------------------------------------------------------------ */ 74 | /* Mega support */ 75 | #if defined(__AVR_ATmega1280__) 76 | /*------------------------------------------------------------------------ */ 77 | /* Onboard LED is connected to pin PB7 on Arduino Mega */ 78 | #if !defined(LED) 79 | #define LED B7 80 | #endif 81 | 82 | /* Ports for soft UART */ 83 | #ifdef SOFT_UART 84 | #define UART_PORT PORTE 85 | #define UART_PIN PINE 86 | #define UART_DDR DDRE 87 | #define UART_TX_BIT 1 88 | #define UART_RX_BIT 0 89 | #endif 90 | #endif 91 | 92 | /* 93 | * ------------------------------------------------------------------------ 94 | * A bunch of macros to enable the LED to be specifed as "B5" for bit 5 95 | * of port B, and similar. 96 | */ 97 | 98 | #define A0 0x100 99 | #define A1 0x101 100 | #define A2 0x102 101 | #define A3 0x103 102 | #define A4 0x104 103 | #define A5 0x105 104 | #define A6 0x106 105 | #define A7 0x107 106 | 107 | #define B0 0x200 108 | #define B1 0x201 109 | #define B2 0x202 110 | #define B3 0x203 111 | #define B4 0x204 112 | #define B5 0x205 113 | #define B6 0x206 114 | #define B7 0x207 115 | 116 | #define C0 0x300 117 | #define C1 0x301 118 | #define C2 0x302 119 | #define C3 0x303 120 | #define C4 0x304 121 | #define C5 0x305 122 | #define C6 0x306 123 | #define C7 0x307 124 | 125 | #define D0 0x400 126 | #define D1 0x401 127 | #define D2 0x402 128 | #define D3 0x403 129 | #define D4 0x404 130 | #define D5 0x405 131 | #define D6 0x406 132 | #define D7 0x407 133 | 134 | #define E0 0x500 135 | #define E1 0x501 136 | #define E2 0x502 137 | #define E3 0x503 138 | #define E4 0x504 139 | #define E5 0x505 140 | #define E6 0x506 141 | #define E7 0x507 142 | 143 | #define F0 0x600 144 | #define F1 0x601 145 | #define F2 0x602 146 | #define F3 0x603 147 | #define F4 0x604 148 | #define F5 0x605 149 | #define F6 0x606 150 | #define F7 0x607 151 | 152 | #define G0 0x700 153 | #define G1 0x701 154 | #define G2 0x702 155 | #define G3 0x703 156 | #define G4 0x704 157 | #define G5 0x705 158 | #define G6 0x706 159 | #define G7 0x707 160 | 161 | #define H0 0x800 162 | #define H1 0x801 163 | #define H2 0x802 164 | #define H3 0x803 165 | #define H4 0x804 166 | #define H5 0x805 167 | #define H6 0x806 168 | #define H7 0x807 169 | 170 | #define J0 0xA00 171 | #define J1 0xA01 172 | #define J2 0xA02 173 | #define J3 0xA03 174 | #define J4 0xA04 175 | #define J5 0xA05 176 | #define J6 0xA06 177 | #define J7 0xA07 178 | 179 | #define K0 0xB00 180 | #define K1 0xB01 181 | #define K2 0xB02 182 | #define K3 0xB03 183 | #define K4 0xB04 184 | #define K5 0xB05 185 | #define K6 0xB06 186 | #define K7 0xB07 187 | 188 | #define L0 0xC00 189 | #define L1 0xC01 190 | #define L2 0xC02 191 | #define L3 0xC03 192 | #define L4 0xC04 193 | #define L5 0xC05 194 | #define L6 0xC06 195 | #define L7 0xC07 196 | 197 | 198 | 199 | #if LED == B0 200 | #undef LED 201 | #define LED_DDR DDRB 202 | #define LED_PORT PORTB 203 | #define LED_PIN PINB 204 | #define LED PINB0 205 | #elif LED == B1 206 | #undef LED 207 | #define LED_DDR DDRB 208 | #define LED_PORT PORTB 209 | #define LED_PIN PINB 210 | #define LED PINB1 211 | #elif LED == B2 212 | #undef LED 213 | #define LED_DDR DDRB 214 | #define LED_PORT PORTB 215 | #define LED_PIN PINB 216 | #define LED PINB2 217 | #elif LED == B3 218 | #undef LED 219 | #define LED_DDR DDRB 220 | #define LED_PORT PORTB 221 | #define LED_PIN PINB 222 | #define LED PINB3 223 | #elif LED == B4 224 | #undef LED 225 | #define LED_DDR DDRB 226 | #define LED_PORT PORTB 227 | #define LED_PIN PINB 228 | #define LED PINB4 229 | #elif LED == B5 230 | #undef LED 231 | #define LED_DDR DDRB 232 | #define LED_PORT PORTB 233 | #define LED_PIN PINB 234 | #define LED PINB5 235 | #elif LED == B6 236 | #undef LED 237 | #define LED_DDR DDRB 238 | #define LED_PORT PORTB 239 | #define LED_PIN PINB 240 | #define LED PINB6 241 | #elif LED == B7 242 | #undef LED 243 | #define LED_DDR DDRB 244 | #define LED_PORT PORTB 245 | #define LED_PIN PINB 246 | #define LED PINB7 247 | 248 | #elif LED == C0 249 | #undef LED 250 | #define LED_DDR DDRC 251 | #define LED_PORT PORTC 252 | #define LED_PIN PINC 253 | #define LED PINC0 254 | #elif LED == C1 255 | #undef LED 256 | #define LED_DDR DDRC 257 | #define LED_PORT PORTC 258 | #define LED_PIN PINC 259 | #define LED PINC1 260 | #elif LED == C2 261 | #undef LED 262 | #define LED_DDR DDRC 263 | #define LED_PORT PORTC 264 | #define LED_PIN PINC 265 | #define LED PINC2 266 | #elif LED == C3 267 | #undef LED 268 | #define LED_DDR DDRC 269 | #define LED_PORT PORTC 270 | #define LED_PIN PINC 271 | #define LED PINC3 272 | #elif LED == C4 273 | #undef LED 274 | #define LED_DDR DDRC 275 | #define LED_PORT PORTC 276 | #define LED_PIN PINC 277 | #define LED PINC4 278 | #elif LED == C5 279 | #undef LED 280 | #define LED_DDR DDRC 281 | #define LED_PORT PORTC 282 | #define LED_PIN PINC 283 | #define LED PINC5 284 | #elif LED == C6 285 | #undef LED 286 | #define LED_DDR DDRC 287 | #define LED_PORT PORTC 288 | #define LED_PIN PINC 289 | #define LED PINC6 290 | #elif LED == C7 291 | #undef LED 292 | #define LED_DDR DDRC 293 | #define LED_PORT PORTC 294 | #define LED_PIN PINC 295 | #define LED PINC7 296 | 297 | #elif LED == D0 298 | #undef LED 299 | #define LED_DDR DDRD 300 | #define LED_PORT PORTD 301 | #define LED_PIN PIND 302 | #define LED PIND0 303 | #elif LED == D1 304 | #undef LED 305 | #define LED_DDR DDRD 306 | #define LED_PORT PORTD 307 | #define LED_PIN PIND 308 | #define LED PIND1 309 | #elif LED == D2 310 | #undef LED 311 | #define LED_DDR DDRD 312 | #define LED_PORT PORTD 313 | #define LED_PIN PIND 314 | #define LED PIND2 315 | #elif LED == D3 316 | #undef LED 317 | #define LED_DDR DDRD 318 | #define LED_PORT PORTD 319 | #define LED_PIN PIND 320 | #define LED PIND3 321 | #elif LED == D4 322 | #undef LED 323 | #define LED_DDR DDRD 324 | #define LED_PORT PORTD 325 | #define LED_PIN PIND 326 | #define LED PIND4 327 | #elif LED == D5 328 | #undef LED 329 | #define LED_DDR DDRD 330 | #define LED_PORT PORTD 331 | #define LED_PIN PIND 332 | #define LED PIND5 333 | #elif LED == D6 334 | #undef LED 335 | #define LED_DDR DDRD 336 | #define LED_PORT PORTD 337 | #define LED_PIN PIND 338 | #define LED PIND6 339 | #elif LED == D7 340 | #undef LED 341 | #define LED_DDR DDRD 342 | #define LED_PORT PORTD 343 | #define LED_PIN PIND 344 | #define LED PIND7 345 | 346 | #elif LED == E0 347 | #undef LED 348 | #define LED_DDR DDRE 349 | #define LED_PORT PORTE 350 | #define LED_PIN PINE 351 | #define LED PINE0 352 | #elif LED == E1 353 | #undef LED 354 | #define LED_DDR DDRE 355 | #define LED_PORT PORTE 356 | #define LED_PIN PINE 357 | #define LED PINE1 358 | #elif LED == E2 359 | #undef LED 360 | #define LED_DDR DDRE 361 | #define LED_PORT PORTE 362 | #define LED_PIN PINE 363 | #define LED PINE2 364 | #elif LED == E3 365 | #undef LED 366 | #define LED_DDR DDRE 367 | #define LED_PORT PORTE 368 | #define LED_PIN PINE 369 | #define LED PINE3 370 | #elif LED == E4 371 | #undef LED 372 | #define LED_DDR DDRE 373 | #define LED_PORT PORTE 374 | #define LED_PIN PINE 375 | #define LED PINE4 376 | #elif LED == E5 377 | #undef LED 378 | #define LED_DDR DDRE 379 | #define LED_PORT PORTE 380 | #define LED_PIN PINE 381 | #define LED PINE5 382 | #elif LED == E6 383 | #undef LED 384 | #define LED_DDR DDRE 385 | #define LED_PORT PORTE 386 | #define LED_PIN PINE 387 | #define LED PINE6 388 | #elif LED == E7 389 | #undef LED 390 | #define LED_DDR DDRE 391 | #define LED_PORT PORTE 392 | #define LED_PIN PINE 393 | #define LED PINE7 394 | 395 | #elif LED == F0 396 | #undef LED 397 | #define LED_DDR DDRF 398 | #define LED_PORT PORTF 399 | #define LED_PIN PINF 400 | #define LED PINF0 401 | #elif LED == F1 402 | #undef LED 403 | #define LED_DDR DDRF 404 | #define LED_PORT PORTF 405 | #define LED_PIN PINF 406 | #define LED PINF1 407 | #elif LED == F2 408 | #undef LED 409 | #define LED_DDR DDRF 410 | #define LED_PORT PORTF 411 | #define LED_PIN PINF 412 | #define LED PINF2 413 | #elif LED == F3 414 | #undef LED 415 | #define LED_DDR DDRF 416 | #define LED_PORT PORTF 417 | #define LED_PIN PINF 418 | #define LED PINF3 419 | #elif LED == F4 420 | #undef LED 421 | #define LED_DDR DDRF 422 | #define LED_PORT PORTF 423 | #define LED_PIN PINF 424 | #define LED PINF4 425 | #elif LED == F5 426 | #undef LED 427 | #define LED_DDR DDRF 428 | #define LED_PORT PORTF 429 | #define LED_PIN PINF 430 | #define LED PINF5 431 | #elif LED == F6 432 | #undef LED 433 | #define LED_DDR DDRF 434 | #define LED_PORT PORTF 435 | #define LED_PIN PINF 436 | #define LED PINF6 437 | #elif LED == F7 438 | #undef LED 439 | #define LED_DDR DDRF 440 | #define LED_PORT PORTF 441 | #define LED_PIN PINF 442 | #define LED PINF7 443 | 444 | #elif LED == G0 445 | #undef LED 446 | #define LED_DDR DDRG 447 | #define LED_PORT PORTG 448 | #define LED_PIN PING 449 | #define LED PING0 450 | #elif LED == G1 451 | #undef LED 452 | #define LED_DDR DDRG 453 | #define LED_PORT PORTG 454 | #define LED_PIN PING 455 | #define LED PING1 456 | #elif LED == G2 457 | #undef LED 458 | #define LED_DDR DDRG 459 | #define LED_PORT PORTG 460 | #define LED_PIN PING 461 | #define LED PING2 462 | #elif LED == G3 463 | #undef LED 464 | #define LED_DDR DDRG 465 | #define LED_PORT PORTG 466 | #define LED_PIN PING 467 | #define LED PING3 468 | #elif LED == G4 469 | #undef LED 470 | #define LED_DDR DDRG 471 | #define LED_PORT PORTG 472 | #define LED_PIN PING 473 | #define LED PING4 474 | #elif LED == G5 475 | #undef LED 476 | #define LED_DDR DDRG 477 | #define LED_PORT PORTG 478 | #define LED_PIN PING 479 | #define LED PING5 480 | #elif LED == G6 481 | #undef LED 482 | #define LED_DDR DDRG 483 | #define LED_PORT PORTG 484 | #define LED_PIN PING 485 | #define LED PING6 486 | #elif LED == G7 487 | #undef LED 488 | #define LED_DDR DDRG 489 | #define LED_PORT PORTG 490 | #define LED_PIN PING 491 | #define LED PING7 492 | 493 | #elif LED == H0 494 | #undef LED 495 | #define LED_DDR DDRH 496 | #define LED_PORT PORTH 497 | #define LED_PIN PINH 498 | #define LED PINH0 499 | #elif LED == H1 500 | #undef LED 501 | #define LED_DDR DDRH 502 | #define LED_PORT PORTH 503 | #define LED_PIN PINH 504 | #define LED PINH1 505 | #elif LED == H2 506 | #undef LED 507 | #define LED_DDR DDRH 508 | #define LED_PORT PORTH 509 | #define LED_PIN PINH 510 | #define LED PINH2 511 | #elif LED == H3 512 | #undef LED 513 | #define LED_DDR DDRH 514 | #define LED_PORT PORTH 515 | #define LED_PIN PINH 516 | #define LED PINH3 517 | #elif LED == H4 518 | #undef LED 519 | #define LED_DDR DDRH 520 | #define LED_PORT PORTH 521 | #define LED_PIN PINH 522 | #define LED PINH4 523 | #elif LED == H5 524 | #undef LED 525 | #define LED_DDR DDRH 526 | #define LED_PORT PORTH 527 | #define LED_PIN PINH 528 | #define LED PINH5 529 | #elif LED == H6 530 | #undef LED 531 | #define LED_DDR DDRH 532 | #define LED_PORT PORTH 533 | #define LED_PIN PINH 534 | #define LED PINH6 535 | #elif LED == H7 536 | #undef LED 537 | #define LED_DDR DDRH 538 | #define LED_PORT PORTH 539 | #define LED_PIN PINH 540 | #define LED PINH7 541 | 542 | #elif LED == J0 543 | #undef LED 544 | #define LED_DDR DDRJ 545 | #define LED_PORT PORTJ 546 | #define LED_PIN PINJ 547 | #define LED PINJ0 548 | #elif LED == J1 549 | #undef LED 550 | #define LED_DDR DDRJ 551 | #define LED_PORT PORTJ 552 | #define LED_PIN PINJ 553 | #define LED PINJ1 554 | #elif LED == J2 555 | #undef LED 556 | #define LED_DDR DDRJ 557 | #define LED_PORT PORTJ 558 | #define LED_PIN PINJ 559 | #define LED PINJ2 560 | #elif LED == J3 561 | #undef LED 562 | #define LED_DDR DDRJ 563 | #define LED_PORT PORTJ 564 | #define LED_PIN PINJ 565 | #define LED PINJ3 566 | #elif LED == J4 567 | #undef LED 568 | #define LED_DDR DDRJ 569 | #define LED_PORT PORTJ 570 | #define LED_PIN PINJ 571 | #define LED PINJ4 572 | #elif LED == J5 573 | #undef LED 574 | #define LED_DDR DDRJ 575 | #define LED_PORT PORTJ 576 | #define LED_PIN PINJ 577 | #define LED PINJ5 578 | #elif LED == J6 579 | #undef LED 580 | #define LED_DDR DDRJ 581 | #define LED_PORT PORTJ 582 | #define LED_PIN PINJ 583 | #define LED PINJ6 584 | #elif LED == J7 585 | #undef LED 586 | #define LED_DDR DDRJ 587 | #define LED_PORT PORTJ 588 | #define LED_PIN PINJ 589 | #define LED PINJ7 590 | 591 | #elif LED == K0 592 | #undef LED 593 | #define LED_DDR DDRK 594 | #define LED_PORT PORTK 595 | #define LED_PIN PINK 596 | #define LED PINK0 597 | #elif LED == K1 598 | #undef LED 599 | #define LED_DDR DDRK 600 | #define LED_PORT PORTK 601 | #define LED_PIN PINK 602 | #define LED PINK1 603 | #elif LED == K2 604 | #undef LED 605 | #define LED_DDR DDRK 606 | #define LED_PORT PORTK 607 | #define LED_PIN PINK 608 | #define LED PINK2 609 | #elif LED == K3 610 | #undef LED 611 | #define LED_DDR DDRK 612 | #define LED_PORT PORTK 613 | #define LED_PIN PINK 614 | #define LED PINK3 615 | #elif LED == K4 616 | #undef LED 617 | #define LED_DDR DDRK 618 | #define LED_PORT PORTK 619 | #define LED_PIN PINK 620 | #define LED PINK4 621 | #elif LED == K5 622 | #undef LED 623 | #define LED_DDR DDRK 624 | #define LED_PORT PORTK 625 | #define LED_PIN PINK 626 | #define LED PINK5 627 | #elif LED == K6 628 | #undef LED 629 | #define LED_DDR DDRK 630 | #define LED_PORT PORTK 631 | #define LED_PIN PINK 632 | #define LED PINK6 633 | #elif LED == K7 634 | #undef LED 635 | #define LED_DDR DDRK 636 | #define LED_PORT PORTK 637 | #define LED_PIN PINK 638 | #define LED PINK7 639 | 640 | #elif LED == L0 641 | #undef LED 642 | #define LED_DDR DDRL 643 | #define LED_PORT PORTL 644 | #define LED_PIN PINL 645 | #define LED PINL0 646 | #elif LED == L1 647 | #undef LED 648 | #define LED_DDR DDRL 649 | #define LED_PORT PORTL 650 | #define LED_PIN PINL 651 | #define LED PINL1 652 | #elif LED == L2 653 | #undef LED 654 | #define LED_DDR DDRL 655 | #define LED_PORT PORTL 656 | #define LED_PIN PINL 657 | #define LED PINL2 658 | #elif LED == L3 659 | #undef LED 660 | #define LED_DDR DDRL 661 | #define LED_PORT PORTL 662 | #define LED_PIN PINL 663 | #define LED PINL3 664 | #elif LED == L4 665 | #undef LED 666 | #define LED_DDR DDRL 667 | #define LED_PORT PORTL 668 | #define LED_PIN PINL 669 | #define LED PINL4 670 | #elif LED == L5 671 | #undef LED 672 | #define LED_DDR DDRL 673 | #define LED_PORT PORTL 674 | #define LED_PIN PINL 675 | #define LED PINL5 676 | #elif LED == L6 677 | #undef LED 678 | #define LED_DDR DDRL 679 | #define LED_PORT PORTL 680 | #define LED_PIN PINL 681 | #define LED PINL6 682 | #elif LED == L7 683 | #undef LED 684 | #define LED_DDR DDRL 685 | #define LED_PORT PORTL 686 | #define LED_PIN PINL 687 | #define LED PINL7 688 | 689 | #elif LED == A0 690 | #undef LED 691 | #define LED_DDR DDRA 692 | #define LED_PORT PORTA 693 | #define LED_PIN PINA 694 | #define LED PINA0 695 | #elif LED == A1 696 | #undef LED 697 | #define LED_DDR DDRA 698 | #define LED_PORT PORTA 699 | #define LED_PIN PINA 700 | #define LED PINA1 701 | #elif LED == A2 702 | #undef LED 703 | #define LED_DDR DDRA 704 | #define LED_PORT PORTA 705 | #define LED_PIN PINA 706 | #define LED PINA2 707 | #elif LED == A3 708 | #undef LED 709 | #define LED_DDR DDRA 710 | #define LED_PORT PORTA 711 | #define LED_PIN PINA 712 | #define LED PINA3 713 | #elif LED == A4 714 | #undef LED 715 | #define LED_DDR DDRA 716 | #define LED_PORT PORTA 717 | #define LED_PIN PINA 718 | #define LED PINA4 719 | #elif LED == A5 720 | #undef LED 721 | #define LED_DDR DDRA 722 | #define LED_PORT PORTA 723 | #define LED_PIN PINA 724 | #define LED PINA5 725 | #elif LED == A6 726 | #undef LED 727 | #define LED_DDR DDRA 728 | #define LED_PORT PORTA 729 | #define LED_PIN PINA 730 | #define LED PINA6 731 | #elif LED == A7 732 | #undef LED 733 | #define LED_DDR DDRA 734 | #define LED_PORT PORTA 735 | #define LED_PIN PINA 736 | #define LED PINA7 737 | 738 | #else 739 | #error ------------------------------------------- 740 | #error Unrecognized LED name. Should be like "B5" 741 | #error ------------------------------------------- 742 | #endif 743 | -------------------------------------------------------------------------------- /stk500.h: -------------------------------------------------------------------------------- 1 | /* STK500 constants list, from AVRDUDE */ 2 | #define STK_OK 0x10 3 | #define STK_FAILED 0x11 // Not used 4 | #define STK_UNKNOWN 0x12 // Not used 5 | #define STK_NODEVICE 0x13 // Not used 6 | #define STK_INSYNC 0x14 // ' ' 7 | #define STK_NOSYNC 0x15 // Not used 8 | #define ADC_CHANNEL_ERROR 0x16 // Not used 9 | #define ADC_MEASURE_OK 0x17 // Not used 10 | #define PWM_CHANNEL_ERROR 0x18 // Not used 11 | #define PWM_ADJUST_OK 0x19 // Not used 12 | #define CRC_EOP 0x20 // 'SPACE' 13 | #define STK_GET_SYNC 0x30 // '0' 14 | #define STK_GET_SIGN_ON 0x31 // '1' 15 | #define STK_SET_PARAMETER 0x40 // '@' 16 | #define STK_GET_PARAMETER 0x41 // 'A' 17 | #define STK_SET_DEVICE 0x42 // 'B' 18 | #define STK_SET_DEVICE_EXT 0x45 // 'E' 19 | #define STK_ENTER_PROGMODE 0x50 // 'P' 20 | #define STK_LEAVE_PROGMODE 0x51 // 'Q' 21 | #define STK_CHIP_ERASE 0x52 // 'R' 22 | #define STK_CHECK_AUTOINC 0x53 // 'S' 23 | #define STK_LOAD_ADDRESS 0x55 // 'U' 24 | #define STK_UNIVERSAL 0x56 // 'V' 25 | #define STK_PROG_FLASH 0x60 // '`' 26 | #define STK_PROG_DATA 0x61 // 'a' 27 | #define STK_PROG_FUSE 0x62 // 'b' 28 | #define STK_PROG_LOCK 0x63 // 'c' 29 | #define STK_PROG_PAGE 0x64 // 'd' 30 | #define STK_PROG_FUSE_EXT 0x65 // 'e' 31 | #define STK_READ_FLASH 0x70 // 'p' 32 | #define STK_READ_DATA 0x71 // 'q' 33 | #define STK_READ_FUSE 0x72 // 'r' 34 | #define STK_READ_LOCK 0x73 // 's' 35 | #define STK_READ_PAGE 0x74 // 't' 36 | #define STK_READ_SIGN 0x75 // 'u' 37 | #define STK_READ_OSCCAL 0x76 // 'v' 38 | #define STK_READ_FUSE_EXT 0x77 // 'w' 39 | #define STK_READ_OSCCAL_EXT 0x78 // 'x' 40 | --------------------------------------------------------------------------------