Skip to content

Instantly share code, notes, and snippets.

@bennadel
Created June 24, 2022 11:30
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save bennadel/619a8811f50ff981a8460b566e6ccde8 to your computer and use it in GitHub Desktop.
Save bennadel/619a8811f50ff981a8460b566e6ccde8 to your computer and use it in GitHub Desktop.
Looking At The Performance Overhead Of A Read-Only Lock In Lucee CFML 5.3.8.201
<cfscript>
coreCount = createObject( "java", "java.lang.Runtime" )
.getRuntime()
.availableProcessors()
;
dump( coreCount );
</cfscript>
With-lock test
Loop Counter: 5263
Value Counter: 10491977
With-lock test
Loop Counter: 4939
Value Counter: 9835909
With-lock test
Loop Counter: 5045
Value Counter: 10060834
With-lock test
Loop Counter: 5358
Value Counter: 10688017
With-lock test
Loop Counter: 5642
Value Counter: 11256738
<cfscript>
// Let's attempt to simulate concurrent request activity all trying to access shared
// data. Each entry in the simulated request will be executed via parallel iteration.
// And, each parallel iteration will try to iterate over the given shared data array.
simulatedRequests = buildArray( 20 );
sharedData = buildArray( 100 );
// Let's keep track of how many test iterations we perform in our test window.
loopCounter = 0;
valueCounter = 0;
// Each test window will be 10-seconds long.
cutoffAt = ( getTickCount() + ( 10 * 1000 ) );
// Let's see how many contentious read operations we can perform in our test window.
while ( getTickCount() < cutoffAt ) {
simulatedRequests.each(
() => {
lock
name = "read-only-lock-test"
type = "readonly"
timeout = 5
{
for ( var increment in sharedData ) {
// CAUTION: The "++" operator is NOT THREAD SAFE. As such, we
// cannot trust the following operation inside a parallel
// iterator. That said, I have it here in order to make sure that
// the Lucee compiler doesn't try to optimize this inner loop
// away. I wanted to make sure that we're consuming the iteration
// value in some way.
valueCounter += increment;
}
}
},
// Run the .each() in parallel using Java's thread pool.
true,
// Maximum number of parallel threads.
simulatedRequests.len()
);
loopCounter++;
};
echo( "With-lock test <br />" );
echo( "Loop Counter: #loopCounter.intValue()# <br />" );
echo( "Value Counter: #valueCounter.intValue()# <br />" );
// ------------------------------------------------------------------------------- //
// ------------------------------------------------------------------------------- //
/**
* I construct an array of the given size in each value is "1".
*/
public array function buildArray( required numeric size ) {
var result = [];
for ( var i = 1 ; i <= size ; i++ ) {
result[ i ] = 1; // All values are 1 (for our counter).
}
return( result );
}
</cfscript>
Without-lock test
Loop Counter: 5397
Value Counter: 10769762
Without-lock test
Loop Counter: 4964
Value Counter: 9895341
Without-lock test
Loop Counter: 5138
Value Counter: 10242939
Without-lock test
Loop Counter: 5296
Value Counter: 10552607
Without-lock test
Loop Counter: 4885
Value Counter: 9740710
<cfscript>
// Let's attempt to simulate concurrent request activity all trying to access shared
// data. Each entry in the simulated request will be executed via parallel iteration.
// And, each parallel iteration will try to iterate over the given shared data array.
simulatedRequests = buildArray( 20 );
sharedData = buildArray( 100 );
// Let's keep track of how many test iterations we perform in our test window.
loopCounter = 0;
valueCounter = 0;
// Each test window will be 10-seconds long.
cutoffAt = ( getTickCount() + ( 10 * 1000 ) );
// Let's see how many contentious read operations we can perform in our test window.
while ( getTickCount() < cutoffAt ) {
simulatedRequests.each(
() => {
for ( var increment in sharedData ) {
// CAUTION: The "++" operator is NOT THREAD SAFE. As such, we cannot
// trust the following operation inside a parallel iterator. That
// said, I have it here in order to make sure that the Lucee compiler
// doesn't try to optimize this inner loop away. I wanted to make sure
// that we're consuming the iteration value in some way.
valueCounter += increment;
}
},
// Run the .each() in parallel using Java's thread pool.
true,
// Maximum number of parallel threads.
simulatedRequests.len()
);
loopCounter++;
}
echo( "Without-lock test <br />" );
echo( "Loop Counter: #loopCounter# <br />" );
echo( "Value Counter: #valueCounter.intValue()# <br />" );
// ------------------------------------------------------------------------------- //
// ------------------------------------------------------------------------------- //
/**
* I construct an array of the given size in each value is "1".
*/
public array function buildArray( required numeric size ) {
var result = [];
for ( var i = 1 ; i <= size ; i++ ) {
result[ i ] = 1; // All values are 1 (for our counter).
}
return( result );
}
</cfscript>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment