* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
- * 1. The above copyright notice and this permission notice shall be
+ * 1. The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
- * 2. If the Software is incorporated into a build system that allows
+ * 2. If the Software is incorporated into a build system that allows
* selection among a list of target devices, then similar target
* devices manufactured by PJRC.COM must be included in the list of
* target devices and selectable in the same manner.
* SOFTWARE.
*/
-#include "mk20dx128.h"
-//#include "HardwareSerial.h"
#include "usb_dev.h"
+#if F_CPU >= 20000000 && defined(NUM_ENDPOINTS)
+
+#include "kinetis.h"
+//#include "HardwareSerial.h"
#include "usb_mem.h"
__attribute__ ((section(".usbbuffers"), used))
usb_packet_t * usb_malloc(void)
{
- unsigned int n, avail;
+ unsigned int n, avail, avail_new;
uint8_t *p;
- __disable_irq();
- avail = usb_buffer_available;
- n = __builtin_clz(avail); // clz = count leading zeros
- if (n >= NUM_USB_BUFFERS) {
- __enable_irq();
- return NULL;
+ do {
+ avail = usb_buffer_available;
+ n = __builtin_clz(avail); // clz = count leading zeros
+ if (n >= NUM_USB_BUFFERS) return NULL;
+
+ //serial_print("malloc:");
+ //serial_phex(n);
+ //serial_print("\n");
+
+ avail_new = avail & ~(0x80000000 >> n);
}
- //serial_print("malloc:");
- //serial_phex(n);
- //serial_print("\n");
+ while (!__sync_bool_compare_and_swap(&usb_buffer_available, avail, avail_new));
- usb_buffer_available = avail & ~(0x80000000 >> n);
- __enable_irq();
p = usb_buffer_memory + (n * sizeof(usb_packet_t));
//serial_print("malloc:");
//serial_phex32((int)p);
}
mask = (0x80000000 >> n);
- __disable_irq();
- usb_buffer_available |= mask;
- __enable_irq();
+ __sync_fetch_and_or(&usb_buffer_available, mask);
//serial_print("free:");
//serial_phex32((int)p);
//serial_print("\n");
}
+#endif // F_CPU >= 20 MHz && defined(NUM_ENDPOINTS)