Submitted by Doug:
patch #7010: Win32 enhanced bitbang_delay * bitbang.c (bitbang_calibrate_delay, bitbang_delay): On Win32, use the high-resolution performance counter rather than the uneducated delay loop guess if it is available on the target hardware. git-svn-id: svn://svn.savannah.nongnu.org/avrdude/trunk/avrdude@894 81a1dc3b-b13d-400b-aceb-764788c761c2
This commit is contained in:
parent
c7f93ef7f1
commit
0433f5e8ef
|
@ -1,3 +1,12 @@
|
||||||
|
2010-01-08 Joerg Wunsch <j.gnu@uriah.heep.sax.de>
|
||||||
|
|
||||||
|
Submitted by Doug:
|
||||||
|
patch #7010: Win32 enhanced bitbang_delay
|
||||||
|
* bitbang.c (bitbang_calibrate_delay, bitbang_delay): On Win32,
|
||||||
|
use the high-resolution performance counter rather than the
|
||||||
|
uneducated delay loop guess if it is available on the target
|
||||||
|
hardware.
|
||||||
|
|
||||||
2010-01-08 Joerg Wunsch <j.gnu@uriah.heep.sax.de>
|
2010-01-08 Joerg Wunsch <j.gnu@uriah.heep.sax.de>
|
||||||
|
|
||||||
Submitted by Gerard:
|
Submitted by Gerard:
|
||||||
|
|
61
bitbang.c
61
bitbang.c
|
@ -42,7 +42,9 @@
|
||||||
|
|
||||||
static int delay_decrement;
|
static int delay_decrement;
|
||||||
|
|
||||||
#if !defined(WIN32NATIVE)
|
#if defined(WIN32NATIVE)
|
||||||
|
static int has_perfcount;
|
||||||
|
#else
|
||||||
static volatile int done;
|
static volatile int done;
|
||||||
|
|
||||||
typedef void (*mysighandler_t)(int);
|
typedef void (*mysighandler_t)(int);
|
||||||
|
@ -53,22 +55,46 @@ static void alarmhandler(int signo)
|
||||||
done = 1;
|
done = 1;
|
||||||
signal(SIGALRM, saved_alarmhandler);
|
signal(SIGALRM, saved_alarmhandler);
|
||||||
}
|
}
|
||||||
#endif /* !WIN32NATIVE */
|
#endif /* WIN32NATIVE */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Calibrate the microsecond delay loop below.
|
* Calibrate the microsecond delay loop below.
|
||||||
*/
|
*/
|
||||||
static void bitbang_calibrate_delay(void)
|
static void bitbang_calibrate_delay(void)
|
||||||
{
|
{
|
||||||
/*
|
|
||||||
* Right now, we don't have any Win32 implementation for this, so we
|
|
||||||
* can only run on a preconfigured delay stepping there. The figure
|
|
||||||
* below should at least be correct within an order of magnitude,
|
|
||||||
* judging from the auto-calibration figures seen on various Unix
|
|
||||||
* systems on comparable hardware.
|
|
||||||
*/
|
|
||||||
#if defined(WIN32NATIVE)
|
#if defined(WIN32NATIVE)
|
||||||
|
static LARGE_INTEGER freq;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If the hardware supports a high-resolution performance counter,
|
||||||
|
* we ultimately prefer that one, as it gives quite accurate delays
|
||||||
|
* on modern high-speed CPUs.
|
||||||
|
*/
|
||||||
|
if (QueryPerformanceFrequency(&freq))
|
||||||
|
{
|
||||||
|
has_perfcount = 1;
|
||||||
|
if (verbose >= 2)
|
||||||
|
fprintf(stderr,
|
||||||
|
"%s: Using performance counter for bitbang delays\n",
|
||||||
|
progname);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* If a high-resolution performance counter is not available, we
|
||||||
|
* don't have any Win32 implementation for setting up the
|
||||||
|
* per-microsecond delay count, so we can only run on a
|
||||||
|
* preconfigured delay stepping there. The figure below should at
|
||||||
|
* least be correct within an order of magnitude, judging from the
|
||||||
|
* auto-calibration figures seen on various Unix systems on
|
||||||
|
* comparable hardware.
|
||||||
|
*/
|
||||||
|
if (verbose >= 2)
|
||||||
|
fprintf(stderr,
|
||||||
|
"%s: Using guessed per-microsecond delay count for bitbang delays\n",
|
||||||
|
progname);
|
||||||
delay_decrement = 100;
|
delay_decrement = 100;
|
||||||
|
}
|
||||||
#else /* !WIN32NATIVE */
|
#else /* !WIN32NATIVE */
|
||||||
struct itimerval itv;
|
struct itimerval itv;
|
||||||
volatile int i;
|
volatile int i;
|
||||||
|
@ -116,10 +142,27 @@ static void bitbang_calibrate_delay(void)
|
||||||
*/
|
*/
|
||||||
void bitbang_delay(int us)
|
void bitbang_delay(int us)
|
||||||
{
|
{
|
||||||
|
#if defined(WIN32NATIVE)
|
||||||
|
LARGE_INTEGER countNow, countEnd;
|
||||||
|
|
||||||
|
if (has_perfcount)
|
||||||
|
{
|
||||||
|
QueryPerformanceCounter(&countNow);
|
||||||
|
countEnd.QuadPart = countNow.QuadPart + freq.QuadPart * us / 1000000ll;
|
||||||
|
|
||||||
|
while (countNow.QuadPart < countEnd.QuadPart)
|
||||||
|
QueryPerformanceCounter(&countNow);
|
||||||
|
}
|
||||||
|
else /* no performance counters -- run normal uncalibrated delay */
|
||||||
|
{
|
||||||
|
#endif /* WIN32NATIVE */
|
||||||
volatile int del = us * delay_decrement;
|
volatile int del = us * delay_decrement;
|
||||||
|
|
||||||
while (del > 0)
|
while (del > 0)
|
||||||
del--;
|
del--;
|
||||||
|
#if defined(WIN32NATIVE)
|
||||||
|
}
|
||||||
|
#endif /* WIN32NATIVE */
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
Loading…
Reference in New Issue