Skip to Main Content
  • Questions
  • How oracle identifies the "Dirty Blocks"

Breadcrumb

Question and Answer

Connor McDonald

Thanks for the question, radsan.

Asked: September 04, 2018 - 4:22 pm UTC

Last updated: September 10, 2018 - 4:54 am UTC

Version: global

Viewed 1000+ times

You Asked

Hello Oracle Masters,
I have a very basic question to understand the internal behavior of oracle. I read couple of blogs and unfortunately end up in confusion; So thought of asking you ..

Assume, i m updaing a block (a record) and not issued the "Commit' .

When check point takes place, database writer writes the dirty blocks to disk.

Question:
say when the same block (un commited) is being queried by another user, how oracle knows "that" particular block is dirty and should be read from "undo" log (to maintain consistency) ?
like, whether oracle maintains a flag in the block header ?

and Connor said...

It is on the block header. You can see this from v$bh,

SQL> alter system flush buffer_cache;

System altered.

SQL> create table t ( x primary key, y ) as select 1 x, 2 y from dual;

Table created.

SQL> select data_object_id from user_objects where object_name = 'T';

DATA_OBJECT_ID
--------------
        101919

SQL>
SQL> select
  2    dbms_rowid.rowid_relative_fno(rowid) f,
  3    dbms_rowid.rowid_block_number(rowid) b
  4  from t;

         F          B
---------- ----------
         7      16259

--
-- here's the freshly created block
--

SQL> select status
  2  from   v$bh
  3  where  file# = 7
  4  and    block# =  16259
  5  and    objd = 101919
  6  /

STATUS
----------
xcur

--
-- if I flush the buffer cache, the block is still "there" but its marked as free, ie, I could replace it
-- with something else
--
SQL> alter system flush buffer_cache;

System altered.

SQL> select status
  2  from   v$bh
  3  where  file# = 7
  4  and    block# =  16259
  5  and    objd = 101919
  6  /

STATUS
----------
free

--
-- I query it back in, and it is the current version of this block because
-- nothing else has ever need to read it consistently
--
SQL> select * from t where x=1;

         X          Y
---------- ----------
         1          2

SQL> select objd, status
  2  from   v$bh
  3  where  file# = 7
  4  and    block# =  16259
  5  and    objd = 101919
  6  /

      OBJD STATUS
---------- ----------
    101919 xcur

--
-- now I delete it (without commit)
--
SQL> delete from t;

SQL> select objd, status, dirty
  2  from   v$bh
  3  where  file# = 7
  4  and    block# =  16259
  5  and    objd = 101919
  6  /

      OBJD STATUS     DIRTY
---------- ---------- -----
    101919 xcur           Y

--
-- and now another session gets an older version of it via a query
--
SQL> select * from t where x=1;

         X          Y
---------- ----------
         1          2

--
-- and we can see the consistent version be created
--

SQL> select objd, status
  2  from   v$bh
  3  where  file# = 7
  4  and    block# =  16259
  5  and    objd = 101919
  6  /

      OBJD STATUS
---------- ----------
    101919 xcur
    101919 cr



But in simplest conceptual form, the SCN can drive all of this.

When I run a query, I am effectively saying "I need all block as of SCN 1234" (ie, SCN when the query started).

As I encounter a block, whether it is dirty or not, committed or not, my requirement will be - is the SCN on this block equal to or before 1234. If it is not, then the block is too "new" for me, being a signal that I need to get an older version of it.

Rating

  (2 ratings)

Is this answer out of date? If it is, please let us know via a Comment

Comments

Thanks Connor, This information created another question for me

radsan, September 06, 2018 - 11:49 am UTC

Thanks Connor for the most useful response.
Unfortunately, This information created another question for me!

My question is regarding to the statement, "When I run a query, I am effectively saying "I need all block as of SCN 1234" (ie, SCN when the query started). "

As per my understanding, SCN increments whenever a commit happens.
So say i connected to a session 'A';
* say DB's current SCN is 1000000 (i understood as SCN is common across database level)
* i am performing an update (say i updated a value in TABLE_A)
still the CURRENT SCN would be 1000000 because i did not commit the txn.
* say the block number B0001 (which holds the data of TABLE_A) Obviously has the SCN 1000000.
* Assume, now check-point happened and writer writes the dirty buffers to disk. Still the SCN of Block B0001 would be 1000000 (bcz commit not issued) but the data in the block would have been changed and status of the block would be marked as "Dirty".

At this point, Say another user connected to a different session (Say SESSION-B) and updating a different table TABLE_B (Note, this is different table) and committed the transaction.

Now the DB's current SCN would be 1000022;
where as
SCN of BLOCK B0001 (which holds the data of TABLE_A) still be 1000000.

So here, if user connected to SESSION-B queries the TABLE_A, then DB Current-SCN would be lesser than the SCN of Block B0001 but the data is inconsistent; right. So Oracle should check the "Status of Block" (Dirty or not) along with the SCN to maintain Consistencey is nt it ?

Please clarify ..
Connor McDonald
September 10, 2018 - 4:54 am UTC

There are two scenarios here (well, there's actually of whole stack but lets keep it at two).

- I encounter committed transactions/data on the block, and hence there is an SCN which tells us whether we need to undo it

- I encounter uncommitted transactions/data on the block, because there is an active transaction recorded in the ITL (interest transaction list) and we definitely have to undo it to get a consistent view because it is uncommitted.

But I stress - vast simplification here. We can have transactions that *look* uncommitted on the block, but are in fact committed.

If you really want dig into it, I suggest "Oracle Core" by Jonathan Lewis.

Thanks Connor

radsan, September 10, 2018 - 3:08 pm UTC

Thanks Connor.. I m interested to read more on this :) .. Will find the book as you suggested ...

More to Explore

Administration

Need more information on Administration? Check out the Administrators guide for the Oracle Database