Problem/possible bug in ext/socket/init.c?

Ruby 1.9.3-p194, Rails 3.1.1, Apache2.2.16, passenger 3.0.14, debian
6.0.5, linux 2.6.32-5-amd64

Recently we’ve encountered a problem with ruby/rack processes that hang
randomly and use 100% of a cpu core while processing requests. This
happens on several linux systems, with our production configuration
listed above. Our system communicates a lot with backend nodes using
bert rpc protocol, so we keep some number of connections needed to serve
a request.

Now, we’ve attached gdb to these processes and found out that they loop
in ext/socket/init.c in wait_connectable. There is a comment that
doesn’t match what I see in the code.

While debugging we’ve seen situations in which either both flags
(RB_WAITFD_IN and RB_WAITFD_OUT) or one of them were set, but not
sockerr (so it looped due to “winsock workaround”). Moreover, applying
the attached patch seems to solve these issues. Note that I kept
original conditions, so they still don’t match what the comment about
the book says. We’ve observed it hanging on connections other than to
our backend.

However, we don’t know what exactly triggers this behavior and how this
code is supposed to work, and this is a stable ruby release after all,
so I feel uneasy about
keeping this patch.

So, does somebody know how this code is supposed to work, what could
trigger this condition, if this possibly is a bug, if so if this fix is
valid and if this change breaks anything obvious? :wink: Or should I write
on the dev list? Thanks.

The comment I refered to:

“Stevens book says, succuessful finish turn on RB_WAITFD_OUT and
failure finish turn on both RB_WAITFD_IN and RB_WAITFD_OUT.”

Our quick patch attached.

Marcin

I’m working with sunspot gem and try create facets dynamically

The problem with facet(:total_view_count) do end block I don’t know
how write code correctly. question is about ruby meta-programming

here is my code:

||| ||Content.search do|
| ||keywords(query)|
| ||with(:community_ids, filtered_community_ids)|
| ||with(:company_id, company.id)|
| ||with(:content_type, content_type) if content_type|
| ||order_by(*order) if order|
| ||paginate(:page => page)|
| ||# begin faceting area|
| ||facet :topic_ids|
| ||facet :community_ids , :only => filtered_community_ids|
| ||facet(:total_view_count) do|
| ||FacetsForSearch.view_facet.each do |range||
| ||row(range[:title]) do|
| ||instance_eval do|
| ||range[:code].call(self)|
| ||end|
| ||end|
| ||end|
| ||end|
| ||end|
||

FacetsForSearch.view_facet - contain hashes with lambda here is the
code

|def view_facet|
| ||[ {:id => ‘view_1’, :title => ‘0 to 100’, :code => lambda{
with(:total_view_count, 0…100) } },|
| ||{:id => ‘view_2’, :title => ‘101 to 200’, :code => lambda{
with(:total_view_count, 101…200) } },|
| ||{:id => ‘view_3’, :title => ‘201 to 300’, :code => lambda{
with(:total_view_count, 201…300) } },|
| ||{:id => ‘view_4’, :title => ‘over 300’, :code => lambda{
with(:total_view_count).greater_than(300) } },|
| ||]|
|end|

Without instance eval code should look like:

| ||facet(:total_view_count) do|
| ||row(‘0_to_100’) do|
| ||with(:total_view_count, 0…100)|
| ||end|
| ||row(‘101_to_200’) do|
| ||with(:total_view_count, 101…200)|
| ||end|
| ||row(‘201_to_300’) do|
| ||with(:total_view_count, 201…300)|
| ||end|
| ||row(‘over_300’) do|
| ||with(:total_view_count).greater_than(300)|
| ||end|
| ||end|

I try replace static code with lambda and can’t figure out how to do
this.
Help!