Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New atomic functions(cas, cog) for shm #1955

Open
wants to merge 2 commits into
base: master
Choose a base branch
from

Conversation

Miniwoffer
Copy link
Contributor

I hereby granted the copyright of the changes in this pull request
to the authors of this lua-nginx-module project.

See: #1954

@xiaocang
Copy link
Contributor

xiaocang commented Nov 1, 2021

Hi, @Miniwoffer I was wondering what the cas and cog abbreviations refer to? seems not very common

@Miniwoffer
Copy link
Contributor Author

cas(compare and swap)
cog(compare or get)

cas refers to the atomic operation(https://en.wikipedia.org/wiki/Compare-and-swap), and is also used by memcached amogst others.
cog is not a common abbreviations, just something derived from cas.

t/167-atomic-shdict.t Outdated Show resolved Hide resolved
t/167-atomic-shdict.t Show resolved Hide resolved
README.markdown Outdated Show resolved Hide resolved
README.markdown Outdated Show resolved Hide resolved
t/167-atomic-shdict.t Outdated Show resolved Hide resolved
@xiaocang
Copy link
Contributor

xiaocang commented Nov 2, 2021

LGTM.

@zhuizhuhaomeng @doujiang24 could you help with this PR ?

src/ngx_http_lua_shdict.c Outdated Show resolved Hide resolved
src/ngx_http_lua_shdict.c Outdated Show resolved Hide resolved
src/ngx_http_lua_shdict.c Outdated Show resolved Hide resolved
src/ngx_http_lua_shdict.c Show resolved Hide resolved
src/ngx_http_lua_shdict.c Show resolved Hide resolved
src/ngx_http_lua_shdict.c Outdated Show resolved Hide resolved
src/ngx_http_lua_shdict.c Outdated Show resolved Hide resolved
src/ngx_http_lua_shdict.c Outdated Show resolved Hide resolved
src/ngx_http_lua_shdict.c Outdated Show resolved Hide resolved
@doujiang24
Copy link
Member

I'm fine with the cas API. We'd better wait for @agentzh 's comment for the cos API.


**context:** *set_by_lua*, rewrite_by_lua*, access_by_lua*, content_by_lua*, header_filter_by_lua*, body_filter_by_lua*, log_by_lua*, ngx.timer.*, balancer_by_lua*, ssl_certificate_by_lua*, ssl_session_fetch_by_lua*, ssl_session_store_by_lua*, ssl_client_hello_by_lua**

Similar to the [get](#ngxshareddictget) method, but only returns if
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What does the "only returns if" part mean? If the if condition is not met, this method will never return? It cannot be. Maybe you mean "will only return the value and the flags" here? And you should also be explicit about what values it returns otherwise (like two nil values?)

The cog name is a bit confusing. How about get_if_not_eq?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah the "only returns if" part is not true.
Maybe something like:

Similar to the [get](#ngxshareddictget) method, but if ``old_value`` and
``old_flags`` match value and flag in dictionary ngx.shared.DICT, 
returns ``nil, true``.

I'm fine with get_if_not_eq

`old_value` or `old_flags` do not match.

If `old_value` or `old_flags` is `nil`
it will be ignored when comparing.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This semantics does not feel right to me. When old value is nil, then it means the expected value in the shdict should also be nil. It should not get ignored? So it always return nil, nilin this case?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The function first lookups the key, and if cant find it return nil, nil.
And after that apply comparison logic.

The reason for the "don't compare nil" is because of old_flags, and i simply tried to have old_value and old_flags act as similar as possible.

For old_flags i added a distinction between 0 and nil simply because it adds more functionality compared to having nil == 0.

Its also the fact that flags cannot exist if value is nil. Does that make flags nil or 0 maybe both maybe neither?

Having different logic where only old_flags is not compared when nil, might be best.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When old value is nil, it should be ignored when comparing (so value could be anything), when old flag is nil, flag is ignored.
This way the api user could have either old_value or old_flag (or both) and whichever is not nil will be compared to the value in shm

@xiaocang
Copy link
Contributor

Hi @Miniwoffer, may I ask if there is a recent update commit in this PR?

@Miniwoffer
Copy link
Contributor Author

Hi @Miniwoffer, may I ask if there is a recent update commit in this PR?

I was waiting for a comment on my answer to @agentzh s question. For some reason my comments are hidden
Screenshot from 2022-01-21 15-58-55

Il just commit my suggestions

  - Added cas(compare and swap) to shdict
  - Added get_if_not_eq to shdict
@Miniwoffer
Copy link
Contributor Author

Miniwoffer commented Jan 31, 2022

@agentzh

In get_if_not_eq, nil for old_value or old_flag is equal to any value.
Why?
It adds more functionality.

In the case of get_if_not_eq(key, nil, flag) if we where to interpret nil
as literal nil it would simply just be a get(key).
But if we interpret nil as any it will act as a get_if_flag_not_eq(key, flag).

Same goes for get_if_not_eq(key, value, nil) this would be the same as
get_if_not_eq(key, value, 0) since 0==nil in shm.
But if we interpret nil as any it would act as a get_if_value_not_eq(key, value)

We could off course add

get_if_value_not_eq(key, value)
get_if_flag_not_eq(key, flag)

and have the same logic, if the API is too unintelligible.

I could also try and rewrite the documentation, if wording similar to nil==any
would help.

@mergify
Copy link

mergify bot commented Mar 15, 2022

This pull request is now in conflict :(

@mergify mergify bot added conflict and removed conflict labels Mar 15, 2022
@LoganDark
Copy link

I would strongly prefer compare_swap over cas, and for the other, compare_get, fetch or something. get_if_not_eq is such a horrible sore to type, I really hope a name like that never makes it into the main release.

@Miniwoffer
Copy link
Contributor Author

@LoganDark
I agree that compare_swap and compare_get are cleaner.
The only disadvantage is that it's less self-documenting.

But then again maybe that can be an advantage, forcing the user not to make assumptions about its functionality.

@xiaocang
Also, this pull request has been idle for a while, and I'm unsure of what to do; is there anything I can do to get the process going?

@LoganDark
Copy link

LoganDark commented Apr 19, 2022

it's less self-documenting

The best thing that can be done for documentation is to ensure the README is complete and up-to-date; this allows the creation of typings:

image

Since the README is already incredibly detailed and useful, I feel like compare_swap is more than good enough. But keep in mind that's just a suggestion. Even I think compare_get is a little weird, and possibly misleading...

But then again maybe that can be an advantage, forcing the user not to make assumptions about its functionality.

I would not consider this an advantage or a disadvantage. Warnings about implementation details belong in the documentation.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants