Jump to content

    

VslavX

Свой
  • Content Count

    1046
  • Joined

  • Last visited

Posts posted by VslavX


  1. другого изделия на STM32F1xx. У нас это решено жестко, введен ID код устройства в каждый загрузчик конкретного устройства, и при несовпадающей по ID прошивке идет соответствующее предупреждение. Получается именно так, что для каждого устройства свой отдельный загрузчик.

    У нас примерно так и решено - только код не на каждый вид устройства, а на конкретную группу устройств. Причем чаще встречается разделение по коду между заказчиками - чтобы они между собой программами не менялись (получали только те софтовые фичи, за которые заплачено, грубо говоря). Таких кодов не очень много (порядка на два меньше чем типов устройств), и для каждого генерируется свой загрузчик (автоматизировано из одних и тех же исходников). Эти коды не зависят от типа процессора - назначаются фиксированно при появлении новой группы, не меняются десятилетиями, и хорошо известны на память всем вовлеченным сотрудникам - при том что сменилось уже несколько поколений процессоров. Процесс выбора загрузчика выглядит так - берем плату, смотрим тип процеcсора - пусть STM32, потом смотрим документы для кого эта партия плат, допустим "Заказчик 8", идем в папку BOOT/STM32 и берем там файл stm32_08.hex. При этом по факту на плате может быть и 100 и 101 и 103-ий процессор - никого на данном этапе это не заботит. Там же лежат автоматизирующие командные файлы, прошить загрузчик в несоответствующий ему процессор (допустим SAM7 в LPC17) практически нереально - утилиты выругаются.

     

    Прошить не соответствующую рабочую прошивку теоретически возможно, такое даже изредка бывает (при разработке, единичные случаи, потому как в серии на конвеере такое не случается), но фатальных последствий не было за 12 лет использования загрузчиков ни разу. В первых изделиях начали было разводить "зоопарк" загрузчиков про который Вы говорите, и делать так же жестко как у Вас, но облом наступил быстро (темп 20-30 разных проектов в год), как выяснилось на практике последствий от неправильной прошивки обычно никаких, поэтому пришли к унифицированному загрузчику. Рабочий код при инициализации перифериии производит несколько проверок и блокируется "в случае чего" (а уж прошивка Cortex на ARM7TDMI виснет просто сразу, STM32/LPC17 виснут еще на инициализации основного генератора), грамотная схема учитывающая начальное состояние после сброса и с помехоподавляющими резисторами не дает палить порты при вероятных конфликтах, ну и загрузчик "всегда живой" и позволяет стереть зашитое "не то" и записать верную прошивку.

     

    Часть заказчиков вообще покупает только софт - им просто процессоры с загрузчиком поставляются, выпускают они свою номенклатуру изделий самостоятельно. Тут без унифицированного загрузчика печалька была бы - поставляется это относительно крупными партиями (логистический гемор с "зарубежом" еще тот), а дальше заказчик смотрит на свои продажи и динамично регулирует свою номенклатуру.

     

    Кстати, внести уникальный код изделия позволяет утилита, которой шьют загрузчики - банально через ключик командной строки. Не обязательно же идентификатор создавать на этапе компиляции - достаточно место для него выделить. Но это тоже как-то на практике не востребовано (ага, уже представил как я начинаю "грузить" производство требованиями зашивать еще один дополнительный код).

     

    В-общем, победил прагматический принцип минимальной достаточности. Времени и людей всегда не хватает, если можно обойтись без "зоопарка", то это следует сделать.

     

     

  2. flash когда я обновляю память программ или память данных flash через свой шифрованных загрузчик(в микроконтроллере), приспособленный под конкретную марку МК, и кабы тут уж все изначально понятно, сколько и какого объема сектора в чипе.

    Да много чего дает, например единый загрузчик - у нас применяются 100, 101 и 103 в разных изделиях, с буквами от 'C' (256К флеша) до 'G' (1M флеша в двух банках). Причем в одно и то же изделие (на ту же печатную плату) , в зависимости от целевого заказчика, могут ставиться разные чипы. Объяснять производству куда какой загрузчик записывать, держать целую базу разных загрузчиков - это все издержки, вероятность ошибок и прочее.

    Также есть набор софтовых-кубиков, например стек USB, прошитый в 100-ый, прочтет ID и аккуратно скажет что "ошиблись адресом" вместо исключения/зависания. В-общем, при имеющейся унификации по софту и железу, определять тип процессора во время исполнения отнюдь не вредно.

     

  3. Судя по всему я ошибся в прочтении - RTX не становится частью CMSIS - она использует RTOS часть CMSIS для себя.

    И это отнюдь не прибавит ей быстродействия :(. Из весомых потенциальных плюсов "любимой жены официальной RTOS для Cortex" - производители контроллеров могут со временем в ROM начать прошивать, сама CMSIS вроде уже в виде ROM в кое-каких контроллерах есть.

     

  4. Уже не нужно. Допилил необходимое для TNKernel.

    Ага, этим только подтверждается тезис про "ушедший поезд". В Вашем случае он "ушел" совсем недавно. А был бы на момент Вашего выбора RTX бесплатным, совсем не факт, что Вы бы на него не перешли.

  5. http://www.keil.com/pr/article/1253.htm

     

    По сути стандартом RTOS для микроконтроллеров ARM де-факто становится RTX. Обещают поддержку Realview, GCC и IAR

    Вроде бы то что Вы искали недавно - бесплатная RTOS с мощной отладкой :)

    ARM-у раздуплится бы лет на 5-7 раньше, когда массово пошли микроконтроллеры на их ядрах - было же ясно, что грядет повальная RTOS-изация. Собственно сама RTOS невеликого объема и сложности программа, было понятно что появится много бесплатных открытых проектов разной степени привлекательности. А теперь народ плотно подсел на все эти варианты и сковырнуть его оттуда "на официальный де-факто стандарт" достаточно непросто. В-общем, поезд ушел, и давно.

    Да и, ИМХО, относительная медленная эта RTX, я на практике не тестировал, только исходники переключения контекста посмотрел, не совсем плохо, но до болида недотягивает. Такты на системные функции в рекламке красиво расписаны, только суть там поглубже немного :).

     

  6. Оп-па.

    Из errat'ы.

    The DBGMCU_IDCODE and DBGMCU_CR debug registers are accessible only in debug

    Такое верно для 101/102/103. В 100 идентификатор читается нормально, 105/107 вроде бы тоже (на практике не пробовал).

     

    Вопрос остается в силе. Как можно узнать размер страницы памяти, кроме как записать/стереть/посмотреть, что получилось.

     

    Есть еще ячейка служебной флеши по адресу 0x1FFFF7E0 (документирована даже - 30-ый раздел "Reference Manual"-а) - там размер флеша указан (если производитель при прошивке своей служебки ненакосячил).

    Ну а полностью узнать какой процессор можно так:

    static DWORD hal_stm32_id(void)
    {
       DWORD fsize, clken, lock;
    
       lock = hal_lock_interrupt();
       {
           DWORD save;
           //
           // Выполняем распознавание 101/102/103 по тактируемым блокам
           // Кратковременно разрешаем тактирование USB и CAN,
           //
           save = RCC_APB1EN;
           RCC_APB1EN  =   save
                         | bRCC_CAN2EN
                         | bRCC_CAN1EN
                         | bRCC_USBEN;
           clken = RCC_APB1EN;
           //
           // Восстанавливаем исходное состояние тактирования
           //
           RCC_APB1EN   = save;
       }
       hal_unlock_interrupt(lock);
    
       if ((clken & bRCC_USBEN) == 0)
       {
           //
           // STM32F101xx - так как нет контроллера USB FS
           //
           clken = 101;
       }
       else
       {
           if ((clken & bRCC_CAN1EN) == 0)
           {
               //
               // STM32F102xx - так как нет контроллера CAN
               //
               clken = 102;
           }
           else
           {
               //
               // Это STM32F103 - так как есть и USB FS и CAN
               //
               clken = 103;
           }
       }
    
       fsize = SYSMEM_FSIZE & 0x0000FFFF;
       switch(DBGMCU_IDCODE & STM32_ID_MASK)
       {
           //
           // Процессоры 101/102/103 - 468BCDE имеют
           // недоступными регистр IDCODE в рабочем
           // режиме - читаются нули (см errata)
           //
           case STM32_ID_000:
           {
               switch(clken)
               {
                   case 101:
                   {
                       switch(fsize)
                       {
                           case 16:    return STM32F101x4_ID;
                           case 32:    return STM32F101x6_ID;
                           case 64:    return STM32F101x8_ID;
                           case 128:   return STM32F101xB_ID;
                           case 256:   return STM32F101xC_ID;
                           case 384:   return STM32F101xD_ID;
                           case 512:   return STM32F101xE_ID;
                       }
                       break;
                   }
                   case 102:
                   {
                       switch(fsize)
                       {
                           case 16:    return STM32F102x4_ID;
                           case 32:    return STM32F102x6_ID;
                           case 64:    return STM32F102x8_ID;
                           case 128:   return STM32F102xB_ID;
                       }
                       break;
                   }
                   case 103:
                   {
                       switch(fsize)
                       {
                           case 16:    return STM32F103x4_ID;
                           case 32:    return STM32F103x6_ID;
                           case 64:    return STM32F103x8_ID;
                           case 128:   return STM32F103xB_ID;
                           case 256:   return STM32F103xC_ID;
                           case 384:   return STM32F103xD_ID;
                           case 512:   return STM32F103xE_ID;
                       }
                       break;
                   }
               }
               break;
           }
           case STM32_ID_420:
           {
               //
               // STM32F100-468B
               //
               switch(fsize)
               {
                   case 16:    return STM32F100x4_ID;
                   case 32:    return STM32F100x6_ID;
                   case 64:    return STM32F100x8_ID;
                   case 128:   return STM32F100xB_ID;
               }
               break;
           }
           case STM32_ID_428:
           {
               //
               // STM32F100-CDE
               //
               switch(fsize)
               {
                   case 256:   return STM32F100xC_ID;
                   case 384:   return STM32F100xD_ID;
                   case 512:   return STM32F100xE_ID;
               }
               break;
           }
           case STM32_ID_410:
           {
               //
               // STM32F10x-8B
               //
               switch(clken)
               {
                   case 101:
                   {
                       switch(fsize)
                       {
                           case 64:    return STM32F101x8_ID;
                           case 128:   return STM32F101xB_ID;
                       }
                       break;
                   }
                   case 102:
                   {
                       switch(fsize)
                       {
                           case 64:    return STM32F102x8_ID;
                           case 128:   return STM32F102xB_ID;
                       }
                       break;
                   }
                   case 103:
                   {
                       switch(fsize)
                       {
                           case 64:    return STM32F103x8_ID;
                           case 128:   return STM32F103xB_ID;
                       }
                       break;
                   }
               }
               break;
           }
           case STM32_ID_412:
           {
               //
               // STM32F10x-46
               //
               switch(clken)
               {
                   case 101:
                   {
                       switch(fsize)
                       {
                           case 16:    return STM32F101x4_ID;
                           case 32:    return STM32F101x6_ID;
                       }
                       break;
                   }
                   case 102:
                   {
                       switch(fsize)
                       {
                           case 16:    return STM32F102x4_ID;
                           case 32:    return STM32F102x6_ID;
                       }
                       break;
                   }
                   case 103:
                   {
                       switch(fsize)
                       {
                           case 16:    return STM32F103x4_ID;
                           case 32:    return STM32F103x6_ID;
                       }
                       break;
                   }
               }
               break;
           }
           case STM32_ID_414:
           {
               //
               // STM32F10x-CDE
               //
               switch(clken)
               {
                   case 101:
                   {
                       switch(fsize)
                       {
                           case 256:   return STM32F101xC_ID;
                           case 384:   return STM32F101xD_ID;
                           case 512:   return STM32F101xE_ID;
                       }
                       break;
                   }
                   case 103:
                   {
                       switch(fsize)
                       {
                           case 256:   return STM32F103xC_ID;
                           case 384:   return STM32F103xD_ID;
                           case 512:   return STM32F103xE_ID;
                       }
                       break;
                   }
               }
               break;
           }
           case STM32_ID_430:
           {
               //
               // STM32F10x-FG
               //
               switch(clken)
               {
                   case 101:
                   {
                       switch(fsize)
                       {
                           case 768:   return STM32F101xF_ID;
                           case 1024:  return STM32F101xG_ID;
                       }
                       break;
                   }
                   case 103:
                   {
                       switch(fsize)
                       {
                           case 768:   return STM32F103xF_ID;
                           case 1024:  return STM32F103xG_ID;
                       }
                       break;
                   }
               }
               break;
           }
           case STM32_ID_418:
           {
               //
               // STM32F105/107 отличаем по блоку Ethernet
               //
               lock = hal_lock_interrupt();
               {
                   DWORD save;
    
                   save = RCC_AHBEN;
                   RCC_AHBEN =   save
                               | bRCC_ETHMACEN;
                   clken = RCC_AHBEN;
                   //
                   // Восстанавливаем исходное состояние тактирования
                   //
                   RCC_AHBEN = save;
               }
               hal_unlock_interrupt(lock);
    
               if (clken & bRCC_ETHMACEN)
               {
                   switch(fsize)
                   {
                       case 128:   return STM32F107xB_ID;
                       case 256:   return STM32F107xC_ID;
                   }
               }
               else
               {
                   switch(fsize)
                   {
                       case 64:    return STM32F105x8_ID;
                       case 128:   return STM32F105xB_ID;
                       case 256:   return STM32F105xC_ID;
                   }
               }
               break;
           }
           case STM32_ID_411:      // F20x/F21x
           case STM32_ID_413:      // F40x/F41x
           {
               //
               // Эти серии в рамках этой функции не поддерживаются
               //
               HAL_ASSERT(FALSE, "Not recognized chip ID");
               break;
           }
       }
       return 0;
    }
    

  7. тестирует каждый кристалл, то маркировка камня и его цена (внутри серии, естественно), определяются тем, какой

    ИМХО, STM32F1xx реально содержит три отдельных серии - 100, 101-103, 105-107, так как они достаточно сильно отличаются друг от друга. А что внутри серии - похоже таки на две-три-четыре размерные ветки, с выбраковкой флеша/ОЗУ до меньшего размера.

     

  8. Хи. А я вот его живьем сейчас включил. На счет T8 пока не знаю, а вот T1 там работает. И кому верить - доке или живому камню. Или они его там просто заглушить забыли ? Бардак какой то.

    Воистину с таймерами китайская грамота. Вот табличка моего составления:

    //________________________________________________________________
    //
    //  Timers, availability
    //
    //              T1  T2-5    T6-7    T8  T9-11   T12-14  T15-17
    //  F100-low    x   x       x       -   -       -       x
    //  F100-med    x   x       x       -   -       -       x
    //  F100-high   x   x       x       -   -       x       x
    //  F101-low    -   x       -       -   -       -       -
    //  F101-med    -   x       -       -   -       -       -
    //  F101-high   x   x       x       x   -       -       -
    //  F101-xl     x   x       x       x   x       x       -
    //  F102-low    -   x       -       -   -       -       -
    //  F102-med    -   x       -       -   -       -       -
    //  F103-low    x   x       -       x   -       -       -
    //  F103-med    x   x       -       x   -       -       -
    //  F103-high   x   x       x       x   -       -       -
    //  F103-xl     x   x       x       x   x       x       -
    //  F105/107    x   x       x       x   -       -       -
    //
    

     

    И еще - у ST последнее время случается путаница в маркировке - попалась партия STM32F103, маркированная как STM32F100 (причем купленно официально). Ага, таймера 12 у 103-го нету, девайс с программой от 100-го подвис.

     

     

    Хи. А я вот его живьем сейчас включил. На счет T8 пока не знаю, а вот T1 там работает. И кому верить - доке или живому камню. Или они его там просто заглушить забыли ? Бардак какой то.

    Наличие таймера (и вообще любого блока) проверяется по биту разрешения тактирования в APBxEN регистре. Ставим бит в единичку - если встал, от блок есть, бит остался нулевой - блока нет.

  9. Среда разработки - кейл, но мне будет достаточно просто какой-нибудь отдельной "терминалки".

    Контроллеры - LPC17xx, LPC11xx.

    Есть своя утилита но под JTAG/ByteBlaster. Скорость вывода отладки зависит от скорости параллельного порта - примерно 350-400кбит/сек. Если интересно - могу поделиться.

     

  10. Конечно получилось, но на самом деле всё это работает не совсем так, как описано в документации.

    Большое спасибо за ответ и пример кода - Вы вселили в меня уверенность :)

    Cегодня утром сделал свой вариант "программной" двойной буферизации. Используется тоже два буфера, только по готовности передатчика "тоглится" не SW_BUF (RX_DTOG) , а статус передатчика (NAK->VALID), ну и при этом предварительно записывается дескриптор второго буфера (это единственный недостаток по сравнению с аппаратным DBL_BUF - запись двух дополнительных слов). Вообще, таким программным методом можно сделать и "тройную" и "квадро" буферизацию - насколько локальной памяти контроллера хватит.

    Потом еще покопался с аппаратной буферизацией. В-общем, дело оказалось в том, что первая транзакция - она не такая как все, и это написано в документации (читать просто нужно было очень внимательно). После первой транзакции передатчик не переходит VALID->NAK если DTOG_TX==SW_BUF и, соответственно не останавливается, - шурует еще следующий буфер и еще один (если SW_BUF не изменить).

    В-общем, сейчас получилось два работающих варианта - двойная аппаратная и N-кратная софтверная буферизации. Анализатор, кстати, отличий на шине не показывает - все транзакции ACK-аются сразу, то есть контроллер и вышележащие слои USB-стека успевают все обработать.

     

     

  11. Имеется STM32F103. В документации на USB-контроллер указана возможность "двойной буферизации" для конечных точек типа Bulk и Iso. Соответственно есть бит DBL_BUF в регистре управления конечной точкой.

     

    Никак не могу заставить нормально работать точку типа Bulk на передачу данных в хост. Если TX_STAT выставить в VALID и рулить только DTOG_RX, то точка не переходит в NAK при равенстве DTOG_RX и DTOG_TX а весело продолжает отдавать в шину данные (смотрелось аппаратным анализатором шины USB). Если начать еще дополнительно рулить статусом TX_STAT, явно загоняя его в NAK, то там цирк вообще начинается - статус может самопроизвольно меняться NAK<->VALID.

     

    Ошибки программы вроде бы исключил, код записи в регистр управления вынесен в отдельный файл, все обращения только через него, единый поток, обложено мутексами, хорошая повторяемость поведения.

     

    Поковырял мусор в виде всяких примеров и китов (это жесть, сколько там какашек, хорошо что вся остальная периферия с полпинка по документации запустилась, не пришлось там копаться раньше), но там нигде не нашел варианта использования двойной буферизации именно для точки типа Bulk (для Iso есть, но это не то). Саппорт помалкивает (флешовый глючный сайт - то отдельная красота).

     

    В связи с этим вопрос такой - у кого-то получилось использовать двойную буферизацию для Bulk согласно написанному в документации? Может кто-то подскажет работающий пример? А то надо решать - копать в этом направлении дальше (искать ошибку) или сделать закат солнца вручную софтверную двойную буферизацию. На передачу вроде несильно проблемно, а с приемом еще неясно (на передачу кучу времени убил) - может оно и работает, надо будет выгребание приостановить и посмотреть, будет ли оно NAK-ить.

  12. Доброго всем времени суток!

    Перехожу с STM32F107 на STM32F217. Столкнулся с такой проблемой на сон грядущий, а именно генерация 50 МГц на MCO pin для подключения PHY по RMII.

    Там еще STM32F2x7 errata такой пунктик содержит:

    "2.7.5 MCO PLL clock pins not compatible with Ethernet IEEE802.3 long term jitter specifications"

     

  13. У меня на Циклоне 2 был случай - слетала PLL (выходила кратковременно из состояния locked). Использовалось несколько выходных фаз PLL, после повторного "залочивания" PLL фазы рассинхронизировались (на произвольгый угол) и плиска шизела.

     

  14. А еще он на сложных, больших, плотных и т.п. проектах падать начинает.

    Да, от многих такое слышал. Но лично у меня падало очень-очень редко - ну раз в месяц и реже. Правда, самая сложная плата была 10-слойка на 5000 пинов, наверное, этого просто недостаточно чтобы "завалить" PCAD.

     

    Потому как большинства нужных правил, для плат такого уровня, в ПКАДе просто не существует.

    Есть такое, поспорить трудно. А быстродействие вполне приемлемое, компы сейчас быстрые, не сравнить как PCAD 4.5 на AT-шке полминуты отрисовывал :)

     

    В общем грустно такие платы в ПКАДе делать:(

    У меня трассировка плат неосновное занятие, и такой сложности платы приходится делать нечасто, поэтому нет смысла осваивать Expedition или Allegro. Более того, я для Expedition прошел весь лабораторный маршрут проектирования простой платы - потратил месяц вечерами на изучение, так меня до сих пор от него тошнит, до того оно громоздкое, глючное и падающее (особенно схемный редактор "доставил"), что вкусняшки разглядывать уже никакого желания не было. Правда, это был еще EE2007, а Ментор свой зоопарк активно улучшает.

     

  15. при условии что схема не будет редактироваться до последнего дня проектирования РСВ.

    Что не будет редактироваться - маловероятно для сложной схемы, да еще надо смотреть насколько качественно ее нарисовали. Если там FPGA, то желательно иметь уже отмоделированный проект с примерной раскладкой по ногам. После трассировки и точной раскладки надо проект опять моделировать - чтобы времянка и аттрибуты ножек FPGA были нужные. У меня был случай почти с десятком итераций на очень простой плате (MAX7160S на PCI, 98-процентное заполнение) - никак проект по времянку не укладывался. Что там за память и чего там на шину повесили - тоже надо смотреть.

    Ну а вообще - ничего фатального или дикого в связке PCAD+HyperLynx нет, все делается и потом спокойно работает. Возможно PCAD и не лучший вариант для высокоскоростных сложных плат, но если к нему привык и есть наработанные библиотеки, то почему бы и нет.

    Upd: заметил что плата еще и довольно плотная - 160x110 на такую кучку не слишком много. Слойность повышенная будет, да и высокотехнологичная - микроотверстия. Но и такое в PCAD делается :)

     

  16. Пишет Window scale: 8 (multiply by 256) - включена вроде. Не пойму как заставить его подтверждения слать скажем раз в 10 сегментов, пока шлет через два. Если бы удалось, все бы как на ладони было видно..

    ИМХО, тут не в подтверждениях дело. Если есть возможность и желание - выложите лог WireShark-а, может что интересное там получится разглядеть. Желательно два варианта - со свичом и без - чтобы разницу было видно.

     

  17. С этим у меня на семерке сложности.. В настройках у меня то, что по умолчанию, т.е.

    А Вы WireShark-ом прихватите траффик и посмотрите что там в сегменте SYN посылается - есть ли там опция масштабирования окна или нет. Заодно посмотрите как там по времени пакеты следуют.

     

  18. LwIP на передающей стороне (процессор Blackfin), на приемной обычная windows 7. Точнее так предполагается делать в конечном варианте, а пока экспериментировал на двух ПК с windows 7.

    Вообще странно, что увеличение размера приемного окна не помогло, по идее этого достаточно должно быть чтобы передающий пачками сегменты гнал.. Если только размер этого самого congestion window никак не вмешивается..

    А Вы TCP опции RFC-1323 для Windows разрешили? ЕМНИП даже для 7-ки надо что-то в реестре патчить. Иначе приемное окно не будет масштабироваться и его размер не превысит 64Кбайт. Вроде бы Congestion Window никак вмешиваться не должен, если нет потерь пакетов.

     

  19. Т.е. вопрос: можно как-то оптимизировать TCP чтобы скорость хотя бы не так быстро падала при увеличении кол-ва свичей? Имеет ли смысл на UDP переходить?

    Буду очень благодарен за помощь

    А какую реализацию TCP используете?

    На время полного оборота пакета (rtt - round-trip-time, AKA "пинг") скорее всего никак повлиять не получится. Но для случаев потоковой передачи сам TCP предусматривает "разгон" с использованием так называемого "окна контроля перегрузки" (congestion window) на передающей стороне. Но не все простые реализации TCP такое поддерживают. Из простых мер можно посоветовать увеличить размер приемного окна сокета TCP на принимающей стороне.

     

  20. Меня эти печи смущают тем что у них нет нижнего подогревателя - большие БГА паять может быть проблемно. Из плюсов у печей то что есть вентилляторы, как я понимаю, для перемешивания горячего воздуха в камере - будет минимальное влияние затенений.

    А отзыва, типа "я купил 962-ую, практические результаты вот такие", на форуме, имхо, не было - я внимательно слежу за этим вопросом.

  21. Сегодня почитывал errata на STM32F217, там есть такой любопытный пункт:

     

    MCO PLL clock pins not compatible with Ethernet IEEE802.3 long term jitter specifications

    Description

    When the clock source output by the microcontroller on the MCO pin is issued from the PLL, the MCO pin cannot be used to deliver a 50 MHz RMII clock input or a 25 MHz MII clock input to the ethernet PHY compliant with the long term jitter maximum value for 1.4 ns specified in the IEEE802.3 standard.

    This limitation applies both to MCO1 and MCO2 pins and PLLs.

    Workaround

    ● In MII mode

    Use a 25 MHz external crystal to generate the HSE clock and output the clock signal on the MCO pin to clock the PHY

    ● In RMII mode

    Either use an external 50 MHz oscillator to clock the PHY or select a PHY with an internal PLL that is able to generate the 50 MHz RMII clock.

    STM32 это, конечно, не LPC17, но примечание, ИМХО, интересное.

     

     

  22. ответ как бы отправляется устройством

    А как Вы определяете что пакет в сеть уходит? Можно взять свитч с функцией Port Mirrorring, и промониторить что именно приходит-уходит на сетевом уровне с устройства. Если пакет из устройства таки уходит, то копать уже саму сеть.

     

    P.S. У меня тоже похожий прикол есть - сайт Микрела на рабочем компе не открывается. Не зависит от браузера, FW нету, VPN нету. Рядом в той же локалке с ноута или другого компа все работает, то есть с маршрутом все OK. Мониторинг WireShark-ом показывает что пропадает первый TCP-пакет высылаемый сервером в ответ на HTTP GET, следующие пакеты за выпавшим приходят нормально, но TCP поток уже разрушен. Почему так - непонятно. Заголовки HTTP-запросов GET от работающего рядом ноута и от проблемного компа - одинаковые (это отметает вопросы по кукам и прочей виновности браузера).

     

  23. Я тоже наступил на эти шикарные грабли. :biggrin:

    Недавно добавил в свой printf поддержку 64-битных целых (signed/unsigned long long которые). Проверил, отладил - все работает. И даже пару месяцев нормально поработало. А потом - хрясь, и все, мусор вместо 64-битных лезть начал. И не сразу докопался я, что va_arg(list, long long) неверно из стека 64-битные вынимает. Добавил выравнивание стека в порт RTOS (TNKernel, не SCM, но это неважно) при инициализации задачи - и все снова работает. Да, грабли просто шикарные, и бьют больно.