This morning, the display on one of my computers was a bit odd. I rebooted the machine and when it came up I got no output on the monitor. I plugged my laptop into the monitor and that worked fine, so it looked like the graphics card had died. I popped down to a local PC store and had the choice of remortgaging my house for new graphics card, or buying a cheap and cheerful one. I did the latter. Even so, the new card was much flasher than the old one.
I put the card in the machine and it booted up and I had a display again. Trouble was, GNOME shell had failed to start and I was knocked back into fallback mode, that looks a bit like GNOME2. Sigh. Forgot to check the the card against support for the ever-so-picky GNOME shell.
I now have a choice to make:
I’m probably going to stick with the last option as I can’t be bothered to waste any more time on this. All of a sudden, Windows and Mac OS X don’t seem so bad after all…
Cheers
Tim…
PS. I don’t need a lecture on why GNOME shell is so picky. I know all the arguments. I’ve read all the crap. Doesn’t mean it’s not a pain in the ass when you buy a newer and more powerful graphics card and you end up with an inferior user experience.
I thought Chronicle was a cool film. Three kids find some weird object and develop super powers. How will it affect them and how will they choose to use them?
It has the “shot on my camcorder” feel, like Cloverfield, and has a kind of Akira feel to me. While I was watching it I kept expecting someone to say, “With great power comes great responsibility!”
The effects are pretty cool. At the start they look like they are going to be a bit low budget, but by the end they get pretty impressive.
Nice mix of teen angst, super powers and destruction. Obviously not targeted for 42 year old men, but it hit the mark for me. I guess that says a lot.
Cheers
Tim…
I just wrote about SQL Injection yesterday - after having giving a web seminar on Wednesday the touched on the topic.
One of the comments on that post was by David Litchfield, he wrote:
#333333; font-family: 'Trebuchet MS', Verdana, Arial, sans-serif; line-height: 18px; text-align: left;">Hey Tom,#333333; font-family: 'Trebuchet MS', Verdana, Arial, sans-serif; line-height: 18px; text-align: left;">Funnily enough I just published a paper about doing the same thing with NUMBER concatenations. This was an addendum to a paper I wrote in 2008 on exploit DATE concatenations - the same problem you discuss here. You can get the recent paper here: http://www.accuvant.com/capability/accuvant-labs/security-research/lateral-sql-injection-revisited-exploiting-numbers and the first paper here: http://www.databasesecurity.com/dbsec/lateral-sql-injection.pdf
I read that new paper and learned something new (actually, much like David - I was kicking myself because I should have been able to see this problem coming as well. It is just a variation on a theme after all). In that paper, he demonstrates how to exploit a SQL Injection flaw using NLS settings with numbers. That is something I hadn't considered before. NLS settings for numbers are different than for dates. With a date, I can set the format string to have any string of characters I want. With numbers - you are very much restricted. On the face of it - it doesn't look like you can exploit a SQL Injection flaw with numbers like you can with dates.
But - you can. Just not as flexibly. But the end result can be as disastrous.
One of the follow on comments to this posting by David was:
#333333; font-family: 'Trebuchet MS', Verdana, Arial, sans-serif; line-height: 18px; text-align: left;">the problem David mentions in #333333; font-family: 'Trebuchet MS', Verdana, Arial, sans-serif; line-height: 18px; text-align: left;">http://www.accuvant.com/capability/accuvant-labs/security-research/lateral-sql-injection-revisited-exploiting-numbers #333333; font-family: 'Trebuchet MS', Verdana, Arial, sans-serif; line-height: 18px; text-align: left;">only arises since NUM_PROC is owned by SYS,#333333; font-family: 'Trebuchet MS', Verdana, Arial, sans-serif; line-height: 18px; text-align: left;">as far as I can see, correct ?
#333333; font-family: 'Trebuchet MS', Verdana, Arial, sans-serif; line-height: 18px; text-align: left;">So, it's not really a problem since nobody ever does something as SYS, correct.
In his example, David used SYS to demonstrate with - which could lead people to believe "ah, it needs SYS to exploit this flaw". But - it doesn't. All it requires is an account with these privileges:
Updated a little later: Let me also say this:
If you use static sql in plsql - your code in plsql cannot be sql injected, period. It is not possible. The only way to get sql injected in plsql is to use dynamic sql - that is the only time. So, if you want maximum protection from SQL Injection - if you just want to avoid it, you will:
a) write your SQL code in PL/SQL
b) call this PL/SQL from your java/c/c#/whatever code USING BINDS to pass all inputs and outputs to/from the database
If you do that - no SQL Injection attacks are possible.
Just a quick reminder that the Rocky Mountain Oracle User Group Training days are just eleven days away. It’s one of the best Oracle events I’ve attended, and I’ll be there again this year. There are plenty of good speakers and interesting presentations on a wide range of topics – and if you’re wandering around between sessions with nothing to do, I’ll be around too and will be happy to say hello and have a chat.
Here’s the list of things I’ve pencilled in on my timetable so far. (Some of the gaps are there because I’m doing three presentations myself, some are there because I haven’t decided what to see yet.)
| Wednesday | 9:15 | Database I/O Performance: Measuring and Planning – Alex Gorbachev, Pythian |
| 10:45 | Parallel Execution in RAC – Riyaj Shamsudeen, OraInternals | |
| 16:00 | Making Sense of Big Data – Gwen Shapira, Pythian | |
| Thursday | 8:30 | Developing and Deploying Extremely Large Databases with Oracle 11gR2 – Daniel Morgan, Morgan’s Library |
| 9:45 | Mining the AWR Repository for Capacity Planning, Visualization, and other Real World Stuff – Karl Arao, Enkitec | |
| 13:30 | Using Oracle Execution Plans for Performance Gains – Janis Griffin, Confio Software |
If nothing else catches your eye, don’t miss out the opportunity to hear Maria Colgan talking about the optimizer. She’s doing three presenations (and only one of them coincides with one of mine) and they’re all worth hearing.
I'll be doing a web seminar on Big Data on February 16th at 10am Pacific Time. Here is the info:
Big Data Essentials: What You Need to Know, February 16th, 10:00 am – 1:30 pm PT
Big data is big news these days. But you don’t base IT investment decisions on magazine headlines.
Join us for the Big Data Online Forum to learn the essentials of big data—from the technology underlying it to real-world use cases. Oracle’s Tom Kyte, Cloudera CEO Mike Olson, and other industry thought leaders will be on hand to explain how big data can deliver revolutionary insight and competitive advantage.
You’ll get answers to tough questions surrounding big data, including:
Register today for this half-day online event featuring live Q&A with big data experts.
I recently did a web seminar on Oracle Database Security (you can see a replay of it here). We had over 1,300 live attendees (glad I couldn't see you all - that would be scary) and the feedback was pretty good.
We also received a few questions, well, actually - a lot of questions. I'm going to try to tackle them here bit by bit. I'm going to start with my favorite topic - questions centered around SQL Injection. I'll center on the core concepts around SQL Injection in this article and then do a followup article regarding the Oracle Database Firewall - a tool useful for detecting and blocking SQL Injection attacks.
During the presentation - I talked about how insidious SQL Injection is - and how hard it can be to detect. In fact, I've written about this before, in this article. The interesting thing about that article on injecting is the very last part of it, the section on "selective system grants". If you read that small section you'll see a comment "Note: Revised contentto prevent SQL injection for this procedure submitted by Roy Jorgensen.". What that means is - the original article I submitted had a SQL Injection bug in it - right after I just spent pages going over SQL Injection! That wasn't too embarrassing was it (it was). But it does point out how easy it is for a SQL Injection bug to sneak into code - even when the coder knows full well what SQL Injection is and how it happens!
Anyway, during the web seminar I talked about a slide I use - with a full stored procedure on it - that contains a SQL Injection bug. I ask the audience, usually full of developers and DBAs to tell me how the code can be SQL Injected.. I tell them right out - this code can be injected and if I were to put it in my schema and grant you execute on it - you could use this to read pretty much any table I own.
I usually hear crickets at this point in time, no hands, no volunteers. Here is the slide:
Note that the input to this procedure is a binary Oracle date - it is fixed length, 7 bytes of data - the century, year, month, day, hour, minute and second. The input is not a string, the input cannot contain things like "or 1=1" - typical SQL Injection attack strings. It can only contain an Oracle date. So - the question is - how can I 'trick' this stored procedure into showing me anything I want to see in the schema that owns the procedure (thus bypassing any and all security the application tier might have put in place - there are no restrictions on what I can and cannot see now).
Before we get there - let's talk about the bit of code that will be problematic - that is line 10. As noted there is a double implicit conversion going on there. That line of code is really:
Where created = to_date( to_char( p_date ) );
Also consider that I said "by default". By default the NLS_DATE_FORMAT is DD-MON-RR (currrently, it has been different in the past!). What happens to this code when someone decides to change it? Your application might well start querying up entirely different data!
always use a bind variable unless you have an excellent technical reason not to - and then you must submit your code for review to at least five people who do not like you - they must be motivated to rip your code apart, critically review it, make fun of it - so they find the bugs.
It’s time for another landmark. The blog has just hit 2,500,000 views (taking three weeks less than the previous half million increment) – here’s a little breakdown on the numbers.
First the top five across the lifetime of the blog:
| AWR / Statspack menu | 40,714 | Updated from time to time |
| NOT IN | 33,983 | Feb 2007 |
| Cartesian Merge Join | 29,633 | Dec 2006 |
| dbms_xplan in 10g | 28,831 | Dec 2006 |
| SQL Profiles (10g) | 21,227 | Feb 2007 |
If we look at just the last year, the top five are:
| AWR / Statspack menu | 18,782 | Updated from time to time |
| NOT IN | 8,916 | Feb 2007 |
| dbms_xplan in 10g | 6,212 | Dec 2006 |
| Oracle Core | 6,181 | Dec 2011 |
| Analysing Statspack (1) | 5,924 | Nov 2006 |
The Cartesian Merge Join has finally been pushed off the top 5 in recent history, but perhaps that’s only a temporary effect while the Addenda to Oracle Core is still fresh in people’s minds. It’s interesting to see how many old articles are still popular reading, though.
The other statistic of note is the number of followers the blog has, currently: 828
While we’re looking at numbers and success stories for the 12 months – the UKOUG annual conference reviews have just come in, and one of mine managed to score 5.83 out of 6 for “Presentation Skills” and 5.65 for content – with one commentator saying:
“Jonathan Lewis is a legend in Oracle circles and now, after my first session with him as speaker, I know why! This was a really well-thought out talk with loads of great ideas and info. My only criticism is that I’d like to attend it again to pick up the bits I missed the first time!”
Don’t worry – it was the one about “Beating the Oracle Optimizer”, 60 minutes featuring seven different strategies for optimising a two-table join, and I’ll be presenting it at least a couple more times in the UK (probably 27th March and 13th June in Manchester and Linlithgow).
I also won two the of UKOUG’s “Inspiring Presenter” awards this year. Not sure I’ll be able to do that again next year since Connor McDonald was in town this year – if you ever get a chance to hear him, make sure you don’t miss it.
The Google Friend Connect badge I’ve been displaying on my website homepage and this blog is no more. Google have canned that widget. Instead it’s been replaced by a Google+ badge. Unfortunately, the G+ badges currently only support Google+ pages, so I can’t connect it to my regular G+ profile, only the ORACLE-BASE.com G+ page. Not ideal, but that’s the way it goes.
Currently, the G+ badge options are not particularly WordPress widget friendly. Even the small option is a bit wider than the width of the sidebar on my blog theme.
I’m not planning on double-posting, so feel free to connect to both profiles if you like. You won’t get everything twice. For the time being, my regular G+ profile is what I’ll be using and the ORACLE-BASE.com G+ page is really only present to support the badge for those people who like to show the site some love.
Cheers
Tim…
It’s always worth browsing through the list of Oracle’s bug fixes each time a new release or patch comes out because it can give you clues about where to look for problems in your production release – and how to anticipate problems on the upgrade. This article is an example of a fix that I found while while looking at the note for 11.2.0.3 quite recently.
Over the last thre or four years I’ve made several commentsabout how subquery factoring could result in changes in execution plans even if the “factored subquery” (or “common table expression” to use the more appropriate technical term) was moved in line. In the 11.2.0.3 bug fixes list, though, you’ll find the following bug fixes:
Bug 11740670 Different execution plans with and without subquery factoring (WITH clause)
Bug 9002661 Transitive predicate were not generated in WITH clause.
So here’s an example that’s been sitting on my laptop for a few years, waiting for the right bug fix (it’s using my standard setup of 8KB block size, LMT with 1MB uniform extents, but not ASSM, and CPU costing disabled):
create table emp (
dept_no not null,
sal,
emp_no,
padding,
constraint e_pk primary key(emp_no)
)
as
select
mod(rownum,6),
rownum,
rownum,
rpad('x',60)
from
all_objects
where
rownum <= 20000
;
-- collect stats, compute, no histograms
select
outer.*
from
emp outer
where
sal > 1000000
and outer.sal > (
select
avg(inner.sal)
from emp inner
where inner.dept_no = outer.dept_no
)
;
with subq as (
select
outer.*
from
emp outer
where
sal > 1000000
and outer.sal > (
select
avg(inner.sal)
from emp inner
where inner.dept_no = outer.dept_no
)
)
select *
from subq
;
In 11.1.0.7 (and earlier) the first version of this query uses a simple filter subquery, and the second version inlines the factored subquery (which should, therefore, produce the same plan) but then unnests the subquery and uses “group by placement” to resolve the plan as a hash join followed by hash aggregation. This gives us two completely different plans:
Plan for first form of the query
------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost |
------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 72 | 70 |
|* 1 | FILTER | | | | |
|* 2 | TABLE ACCESS FULL | EMP | 1 | 72 | 35 |
| 3 | SORT AGGREGATE | | 1 | 8 | |
|* 4 | TABLE ACCESS FULL| EMP | 3333 | 26664 | 35 |
------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - filter("OUTER"."SAL"> (SELECT AVG("INNER"."SAL") FROM "EMP"
"INNER" WHERE "INNER"."DEPT_NO"=:B1))
2 - filter("SAL">1000000)
4 - filter("INNER"."DEPT_NO"=:B1)
Plan with factored subquery moved in line
-------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost |
-------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 83 | 93 |
|* 1 | FILTER | | | | |
| 2 | HASH GROUP BY | | 1 | 83 | 93 |
|* 3 | HASH JOIN | | 1667 | 135K| 71 |
|* 4 | TABLE ACCESS FULL| EMP | 1 | 72 | 35 |
| 5 | TABLE ACCESS FULL| EMP | 20000 | 214K| 35 |
-------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - filter("OUTER"."SAL">AVG("INNER"."SAL"))
3 - access("INNER"."DEPT_NO"="OUTER"."DEPT_NO")
4 - filter("SAL">1000000)
Under 11.2.0.3, however, the first plan appears for both forms of the query.
On the plus side – this is good, because Oracle is now behaving consistently. On the minus side – this is bad, because someone, somewhere, is going to be the unlucky person who managed to get a good execution plan by accident because of the bugs.
Maxim: when upgrading to 11.2.0.3, keep a close eye on any queries you’ve got that include subquery factoring – in fact, you might decide to capture SQL Baselines (without activating them) for every single one of them before doing the upgrade so that you can enforce the pre-upgrade plan if the post-upgrade plan is less efficient.
Footnote: I haven’t finished with this example – there’s an interesting follow-up that appeared in the remainder of my test code when I hinted the subquery into materialization. But that’s a story for another day.
We’ve just booked the first European venue for the Understanding Storage Masterclass. I will be presenting the Masterclass on April 24/25 2012 at Prospero House in London, tickets are available HERE. I’m pretty excited to host this training session in my home country, and I hope to see you there!
Recent comments
2 weeks 2 days ago
4 weeks 6 days ago
5 weeks 1 day ago
22 weeks 3 days ago
30 weeks 3 days ago
1 year 4 weeks ago
1 year 5 weeks ago
1 year 10 weeks ago
1 year 10 weeks ago
1 year 11 weeks ago