summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEliot Horowitz <eliot@10gen.com>2010-01-16 11:16:30 -0500
committerEliot Horowitz <eliot@10gen.com>2010-01-16 11:16:30 -0500
commit53b5dae92e8c045f6aa94add14dc0564ee9ee6e9 (patch)
treedcf09d3e7eab9832962a5c3f88f98d94447f8e40
parent6830dd0dd0462492ec0547050fb0eeb2908591b3 (diff)
downloadmongo-53b5dae92e8c045f6aa94add14dc0564ee9ee6e9.tar.gz
check for bad $set where set to an object with a . SERVER-261
-rw-r--r--db/update.cpp1
-rw-r--r--db/update.h13
-rw-r--r--jstests/set1.js2
3 files changed, 14 insertions, 2 deletions
diff --git a/db/update.cpp b/db/update.cpp
index bba3b54d1e8..0a3688a75e9 100644
--- a/db/update.cpp
+++ b/db/update.cpp
@@ -57,6 +57,7 @@ namespace mongo {
}
case SET: {
+ _checkForAppending( elt );
b.appendAs( elt , shortFieldName );
break;
}
diff --git a/db/update.h b/db/update.h
index 74e0eb372c2..3597e955947 100644
--- a/db/update.h
+++ b/db/update.h
@@ -146,6 +146,17 @@ namespace mongo {
bb.append( elt );
bb.done();
}
+
+ void _checkForAppending( BSONElement& e ){
+ if ( e.type() == Object ){
+ // this is a tiny bit slow, but rare and important
+ // only when setting something TO an object, not setting something in an object
+ // and it checks for { $set : { x : { 'a.b' : 1 } } }
+ // which is feel has been common
+ uassert( 12527 , "not okForStorage" , e.embeddedObject().okForStorage() );
+ }
+ }
+
};
class ModSet {
@@ -173,7 +184,6 @@ namespace mongo {
void _appendNewFromMods( const string& root , Mod& m , BSONObjBuilder& b , set<string>& onedownseen );
void appendNewFromMod( Mod& m , BSONObjBuilder& b ){
-
switch ( m.op ){
case Mod::PUSH: {
@@ -198,6 +208,7 @@ namespace mongo {
case Mod::INC:
case Mod::SET: {
+ m._checkForAppending( m.elt );
b.appendAs( m.elt, m.shortFieldName );
break;
}
diff --git a/jstests/set1.js b/jstests/set1.js
index 2af01e66bfc..d741387af58 100644
--- a/jstests/set1.js
+++ b/jstests/set1.js
@@ -4,6 +4,6 @@ t.drop();
t.insert( { _id : 1, emb : {} });
t.update( { _id : 1 }, { $set : { emb : { 'a.dot' : 'data'} }});
+assert.eq( { _id : 1 , emb : {} } , t.findOne() , "A" );
-printjson( t.findOne() ); // SERVER-261