diff --git a/modules/Bio/EnsEMBL/DBSQL/ExonAdaptor.pm b/modules/Bio/EnsEMBL/DBSQL/ExonAdaptor.pm
index 0d7c69c15395ad95619d4eceb18823bd37702111..f485d78677f185ef4132811e745d3d6555707517 100644
--- a/modules/Bio/EnsEMBL/DBSQL/ExonAdaptor.pm
+++ b/modules/Bio/EnsEMBL/DBSQL/ExonAdaptor.pm
@@ -745,6 +745,15 @@ FEATURE: while ( $sth->fetch() ) {
 
       } ## end else [ if ( $dest_slice_strand...)]
 
+      # Throw away features off the end of the requested slice or on
+      # different seq_region.
+      if (   $seq_region_end < 1
+	     || $seq_region_start > $dest_slice_length
+	     || ($dest_slice_sr_id ne $seq_region_id))
+	{
+	  next FEATURE;
+	}
+
       $slice = $dest_slice;
     } ## end if ( defined($dest_slice...))
 
diff --git a/modules/Bio/EnsEMBL/DBSQL/GeneAdaptor.pm b/modules/Bio/EnsEMBL/DBSQL/GeneAdaptor.pm
index 2371efca2f5b23c277604148eb682d3ad3e8bfcd..f73403a8b799838687c8846a0d764ac66d0772ff 100644
--- a/modules/Bio/EnsEMBL/DBSQL/GeneAdaptor.pm
+++ b/modules/Bio/EnsEMBL/DBSQL/GeneAdaptor.pm
@@ -1706,6 +1706,15 @@ FEATURE: while ($sth->fetch()) {
 
 	  } ## end else [ if ($dest_slice_strand...)]
 
+	  # Throw away features off the end of the requested slice or on
+          # different seq_region.
+          if (   $seq_region_end < 1
+                  || $seq_region_start > $dest_slice_length
+                  || ($dest_slice_sr_id ne $seq_region_id))
+          {
+                next FEATURE;
+          }
+
 	  $slice = $dest_slice;
 	} ## end if (defined($dest_slice...))
 
diff --git a/modules/Bio/EnsEMBL/DBSQL/SimpleFeatureAdaptor.pm b/modules/Bio/EnsEMBL/DBSQL/SimpleFeatureAdaptor.pm
index b89ed5adc8f5e92766594f9cd2de30a0fec55864..0da22bef2e3400ab8d6e0f09e05b05f17eeb4572 100644
--- a/modules/Bio/EnsEMBL/DBSQL/SimpleFeatureAdaptor.pm
+++ b/modules/Bio/EnsEMBL/DBSQL/SimpleFeatureAdaptor.pm
@@ -303,24 +303,112 @@ sub _objs_from_sth {
     # If the dest_slice starts at 1 and is foward strand, nothing needs doing
     #
     if($dest_slice) {
-      if($dest_slice_start != 1 || $dest_slice_strand != 1) {
-        if($dest_slice_strand == 1) {
-          $seq_region_start = $seq_region_start - $dest_slice_start + 1;
-          $seq_region_end   = $seq_region_end   - $dest_slice_start + 1;
-        } else {
-          my $tmp_seq_region_start = $seq_region_start;
-          $seq_region_start = $dest_slice_end - $seq_region_end + 1;
-          $seq_region_end   = $dest_slice_end - $tmp_seq_region_start + 1;
-          $seq_region_strand *= -1;
-        }
-      }
-       
-      #throw away features off the end of the requested slice
-      if($seq_region_end < 1 || $seq_region_start > $dest_slice_length ||
-	( $dest_slice_seq_region_id != $seq_region_id )) {
-#	print STDERR "IGNORED DUE TO CUTOFF  $dest_slice_seq_region_id ne $seq_region_id . $sr_name\n";
+      my $seq_region_len = $dest_slice->seq_region_length();
+
+      if ($dest_slice_strand == 1) { # Positive strand
+		
+	$seq_region_start = $seq_region_start - $dest_slice_start + 1;
+	$seq_region_end   = $seq_region_end - $dest_slice_start + 1;
+
+	if ($dest_slice->is_circular()) {
+	  # Handle cicular chromosomes.
+
+	  if ($seq_region_start > $seq_region_end) {
+	    # Looking at a feature overlapping the chromsome origin.
+
+	    if ($seq_region_end > $dest_slice_start) {
+
+	      # Looking at the region in the beginning of the
+	      # chromosome.
+	      $seq_region_start -= $seq_region_len;
+	    }
+
+	    if ($seq_region_end < 0) {
+	      $seq_region_end += $seq_region_len;
+	    }
+
+	  } else {
+
+	    if (   $dest_slice_start > $dest_slice_end
+		   && $seq_region_end < 0) {
+	      # Looking at the region overlapping the chromosome
+	      # origin and a feature which is at the beginning of the
+	      # chromosome.
+	      $seq_region_start += $seq_region_len;
+	      $seq_region_end   += $seq_region_len;
+	    }
+	  }
+
+	}		       ## end if ($dest_slice->is_circular...)
+
+      } else {			# Negative strand
+
+	my $start = $dest_slice_end - $seq_region_end + 1;
+	my $end = $dest_slice_end - $seq_region_start + 1;
+
+	if ($dest_slice->is_circular()) {
+
+	  if ($dest_slice_start > $dest_slice_end) { 
+	    # slice spans origin or replication
+
+	    if ($seq_region_start >= $dest_slice_start) {
+	      $end += $seq_region_len;
+	      $start += $seq_region_len 
+		if $seq_region_end > $dest_slice_start;
+
+	    } elsif ($seq_region_start <= $dest_slice_end) {
+	      # do nothing
+	    } elsif ($seq_region_end >= $dest_slice_start) {
+	      $start += $seq_region_len;
+	      $end += $seq_region_len;
+
+	    } elsif ($seq_region_end <= $dest_slice_end) {
+
+	      $end += $seq_region_len
+		if $end < 0;
+
+	    } elsif ($seq_region_start > $seq_region_end) {
+		  
+	      $end += $seq_region_len;
+
+	    } else {
+		  
+	    }
+      
+	  } else {
+
+	    if ($seq_region_start <= $dest_slice_end and $seq_region_end >= $dest_slice_start) {
+	      # do nothing
+	    } elsif ($seq_region_start > $seq_region_end) {
+	      if ($seq_region_start <= $dest_slice_end) {
+	  
+		$start -= $seq_region_len;
+
+	      } elsif ($seq_region_end >= $dest_slice_start) {
+		$end += $seq_region_len;
+
+	      } else {
+		    
+	      }
+	    }
+	  }
+
+	}
+
+	$seq_region_start = $start;
+	$seq_region_end = $end;
+	$seq_region_strand *= -1;
+
+      }	## end else [ if ($dest_slice_strand...)]
+
+      # Throw away features off the end of the requested slice or on
+      # different seq_region.
+      if (   $seq_region_end < 1
+	     || $seq_region_start > $dest_slice_length
+	     || ($dest_slice_seq_region_id ne $seq_region_id)) {
 	next FEATURE;
       }
+
       $slice = $dest_slice;
     }
 
diff --git a/modules/Bio/EnsEMBL/DBSQL/TranscriptAdaptor.pm b/modules/Bio/EnsEMBL/DBSQL/TranscriptAdaptor.pm
index 000e9f2b615a04a47f36e1223b7dafc54b9385d1..8aaea4181d1011f646eb95a301460d69d413c794 100644
--- a/modules/Bio/EnsEMBL/DBSQL/TranscriptAdaptor.pm
+++ b/modules/Bio/EnsEMBL/DBSQL/TranscriptAdaptor.pm
@@ -1693,6 +1693,15 @@ sub _objs_from_sth {
 
       } ## end else [ if ( $dest_slice_strand...)]
 
+      # Throw away features off the end of the requested slice or on
+      # different seq_region.
+      if (   $seq_region_end < 1
+	     || $seq_region_start > $dest_slice_length
+	     || ($dest_slice_sr_id ne $seq_region_id))
+	{
+	  next FEATURE;
+	}
+      
       $slice = $dest_slice;
     }